오나전 탐색 알고리즘 이다.
간단하게, 4자리 숫자 하나를 찾아야 한다면, 0000부터 9999까지 모두 넣어 본다는 뜻이다.
비밀 번호 해킹할 떄 사용하면 좋다.
간단하고 직관적이지만, 모든 경우를 다 시도하기 깨문에, 시간이 많이 들어가 비효율 적 일 수 있다.
문제의 크기가 작거나, 최적의 해답이 필요없는 상황에선 나이스하게 사용할 수 있다.
간단하게, text 에서 특정 패턴이 존재하는지 찾아서 위피를 반환하는 프로그램 예실르 보자.
public class RecursiveBruteForce {
// 재귀적으로 텍스트의 각 위치에서 패턴을 비교하는 메서드
public static int recursiveSearch(String text, String pattern, int textIndex, int patternIndex) {
// 패턴의 모든 문자가 일치했을 경우 시작 위치 반환
if (patternIndex == pattern.length()) {
return textIndex - patternIndex;
}
// 텍스트의 끝에 도달했거나 문자가 일치하지 않으면 -1 반환
if (textIndex == text.length() || text.charAt(textIndex) != pattern.charAt(patternIndex)) {
return -1;
}
// 다음 문자 비교
return recursiveSearch(text, pattern, textIndex + 1, patternIndex + 1);
}
// 텍스트의 각 위치를 시작점으로 패턴을 찾는 메서드
public static int findPattern(String text, String pattern, int startIndex) {
// 텍스트의 남은 부분이 패턴보다 짧을 경우 더 이상 탐색할 필요 없음
if (startIndex > text.length() - pattern.length()) {
return -1;
}
// 현재 위치에서 패턴을 찾기 시도
int result = recursiveSearch(text, pattern, startIndex, 0);
// 패턴이 일치하면 그 위치 반환, 그렇지 않으면 다음 위치에서 재귀적으로 탐색
if (result != -1) {
return result;
} else {
return findPattern(text, pattern, startIndex + 1);
}
}
public static void main(String[] args) {
String text = "Hello, this is a simple example.";
String pattern = "simple";
// findPattern 메서드를 호출하여 패턴의 시작 위치를 찾음
int result = findPattern(text, pattern, 0);
if (result != -1) {
System.out.println("Pattern found at index: " + result);
} else {
System.out.println("Pattern not found.");
}
}
}
위 코드를 보면,
이런 구성이다.
위 코드의 주축인 재귀 함수를 알아보자면,
그냥 함수 스스로가 지를 호출한는 함수이다.
위의 코드에도 스스로를 함수 내에서 호출한다.
함숭서 빠져나오지 않으면 오버플로우가 생기기 때문에 꼭 빠져나오는 트리거를 준비해야 한다.
예제를 보자면,
public class FactorialExample {
// 재귀적으로 팩토리얼을 계산하는 함수
public static int factorial(int n) {
// 기본 조건: n이 0이면 1 반환 (0! = 1)
if (n == 0) {
return 1;
}
// 재귀 호출: n * (n-1)!
return n * factorial(n - 1);
}
public static void main(String[] args) {
int number = 5;
int result = factorial(number);
System.out.println("Factorial of " + number + " is: " + result);
}
}
factorial 함수는 자기 자신을 호출하여 n!을 계산합니다. n이 0이 되면 재귀 호출이 종료되고, 그동안의 계산된 값들이 반환한다.
반복문과 비교를 해 보자면,
재귀함수 사용시기만을 보면,
그 유명한 피보니치 수열을 재귀적으로 해보자.
public class FibonacciExample {
// 재귀적으로 피보나치 수열을 계산하는 함수
public static int fibonacci(int n) {
// 기본 조건: n이 0 또는 1일 경우 그 값을 반환
if (n == 0 || n == 1) {
return n;
}
// 재귀 호출: (n-1)번째와 (n-2)번째 피보나치 수를 더함
return fibonacci(n - 1) + fibonacci(n - 2);
}
public static void main(String[] args) {
int number = 10;
int result = fibonacci(number);
System.out.println("Fibonacci number at position " + number + " is: " + result);
}
}
위의 방법으로 간단하게 피보니치 수열을 재귀적으로 해결할 수 있다.
정말 좋은 재귀함수지만, 단점도 있다.
재귀를 피해야 할 때는
이런 상황에서는 반복문이나 메모이제이션 같은 기법을 사용하는 것이 더 나을 수 있다.