📚
재귀호출
May 27, 2023
메소드 내부에서 메소드 자신을 다시 호출하는 것
어떻게 메소드가 자기 자신을 호출할 수 있는걸까?
메소드 입장에서는 자기 자신을 호출하는 것과 다른 메소드를 호출하는 것은 차이가 없다. ‘메소드 호출’ 이라는 것이 특정 위치에 저장되어 있는 명령들을 수행하는 것일 뿐이기 때문
호출된 메소드는 원래의 값이 아닌 복사된 값으로 작업하기 때문에 호출한 메소드와 관계없이 독립적인 작업 수행이 가능하다 : 값에 의한 호출(call by value)
재귀호출과 반복문
재귀호출은 반복문과 유사한 점이 많으며, 대부분의 재귀호출은 반복문으로 작성하는것이 가능하다. 어떤 작업을 반복적으로 처리해야한다면, 먼저 반복문으로 작성해보고 너무 복잡하다면 재귀호출로 간단하게 할 수 없는지 고민해봐야한다. 반복문보다 재귀호출이 비효율적이므로 재귀호출에 드는 비용보다 재귀호출의 간결함이 주는 이득이 충분히 큰 경우에만 사용해야한다.
대표적인 재귀호출 : 팩토리얼
팩토리얼은 한 숫자가 1이 될 때까지 1씩 감소시켜가면서 계속해서 곱해 나가는 것
class FactorialTest {
public static void main(String args[]) {
System.out.println(factorial(2)); // 1
}
static long factorial(int n) {
long result=0;
if (n == 1) return 1; //3
return n * factorial(n-1); //다시 자기 자신을 호출한다. //2
}
}
factorial(2)
를 호출하면서 매개변수 n에 2가 복사된다.return 2 * factorial(1)
로 인해서factorial(1)
이 호출되고 매개변수 n에 1이 복사된다.- if문이 참이므로 1을 반환하면서 메소드는 종료되며,
factorial(1)
를 호출한 곳으로 돌아간다. return 2 * factorial(1)
→return 2 * 1
의 과정으로 계산되어 결과값 2가 반환된다.
매개변수 n의 값이 0일경우 위 코드의 if문이 절대 참이 될 수 없기 때문에 계속해서 재귀호출만 일어날 뿐 메소드가 종료되지 않아서 스택에 계속 데이터가 쌓이게 되고 스택오버플로우 에러가 발생하게 된다. 이러한 에러를 방지하기 위해 매개변수의 유효성을 검사해야한다.