반응형
이진 탐색(Binary Search)
이진 탐색(Binary Search)은 정렬된 배열에서 원하는 값을 빠르게 찾아내는 효율적인 알고리즘입니다. 이진 탐색은 중간값을 반복적으로 비교하며 탐색 범위를 반으로 줄여 나가므로, 데이터의 크기가 클수록 매우 효과적입니다.
1. 이진 탐색의 개념
이진 탐색은 다음의 과정을 통해 동작합니다:
- 배열의 중간값을 확인합니다.
- 찾고자 하는 값이 중간값보다 작으면 탐색 범위를 왼쪽 절반으로 좁힙니다.
- 찾고자 하는 값이 중간값보다 크면 탐색 범위를 오른쪽 절반으로 좁힙니다.
- 원하는 값을 찾을 때 까지 위 과정을 반복합니다.
이진 탐색은 정렬된 배열에서만 동작한다는 점에 유의해야 합니다.
2. 이진 탐색의 동작 원리
- 초기 배열: [1, 3, 5, 7, 9, 11], 찾고자 하는 값: 7
- 중간값 계산: (0 + 5) / 2 = 2 → 중간값: 5
- 7 > 5 이므로 오른쪽 절반 탐색: [7, 9, 11]
- 다시 중간값 계산: (3 + 5) / 2 = 4 → 중간값: 9
- 7 < 9 이므로 왼쪽 절반 탐색: [7]
- 값 7을 찾음.
반응형
3. Upper Bound와 Lower Bound
Lower Bound
- Lower Bound는 배열에서 찾고자 하는 값 이상이 처음 나타나는 위치를 반환합니다.
- 예를 들어, 배열 [1, 2, 4, 4, 5]에서 값 4의 Lower Bound는 인덱스 2입니다.
Upper Bound
- Upper Bound는 배열에서 찾고자 하는 값보다 큰 값이 처음 나타나는 위치를 반환합니다.
- 예를 들어, 배열 [1, 2, 4, 4, 5]에서 값 4의 Upper Bound는 인덱스 4입니다.
4. 이진 탐색 구현 예시 코드
C 언어 구현
#include <stdio.h>
int binarySearch(int arr[], int size, int target) {
int left = 0, right = size - 1;
while (left <= right) {
int mid = left + (right - left) / 2;
if (arr[mid] == target)
return mid;
else if (arr[mid] < target)
left = mid + 1;
else
right = mid - 1;
}
return -1;
}
int lowerBound(int arr[], int size, int target) {
int left = 0, right = size;
while (left < right) {
int mid = left + (right - left) / 2;
if (arr[mid] < target)
left = mid + 1;
else
right = mid;
}
return left;
}
int upperBound(int arr[], int size, int target) {
int left = 0, right = size;
while (left < right) {
int mid = left + (right - left) / 2;
if (arr[mid] <= target)
left = mid + 1;
else
right = mid;
}
return left;
}
int main() {
int arr[] = {1, 2, 4, 4, 5};
int size = sizeof(arr) / sizeof(arr[0]);
printf("Lower Bound of 4: %d\n", lowerBound(arr, size, 4));
printf("Upper Bound of 4: %d\n", upperBound(arr, size, 4));
return 0;
}
Java 구현
import java.util.*;
public class BinarySearch {
public static int binarySearch(int[] arr, int target) {
int left = 0, right = arr.length - 1;
while (left <= right) {
int mid = left + (right - left) / 2;
if (arr[mid] == target)
return mid;
else if (arr[mid] < target)
left = mid + 1;
else
right = mid - 1;
}
return -1;
}
public static int lowerBound(int[] arr, int target) {
int left = 0, right = arr.length;
while (left < right) {
int mid = left + (right - left) / 2;
if (arr[mid] < target)
left = mid + 1;
else
right = mid;
}
return left;
}
public static int upperBound(int[] arr, int target) {
int left = 0, right = arr.length;
while (left < right) {
int mid = left + (right - left) / 2;
if (arr[mid] <= target)
left = mid + 1;
else
right = mid;
}
return left;
}
public static void main(String[] args) {
int[] arr = {1, 2, 4, 4, 5};
System.out.println("Lower Bound of 4: " + lowerBound(arr, 4));
System.out.println("Upper Bound of 4: " + upperBound(arr, 4));
}
}
Python 구현
def binary_search(arr, target):
left, right = 0, len(arr) - 1
while left <= right:
mid = left + (right - left) // 2
if arr[mid] == target:
return mid
elif arr[mid] < target:
left = mid + 1
else:
right = mid - 1
return -1
def lower_bound(arr, target):
left, right = 0, len(arr)
while left < right:
mid = (left + right) // 2
if arr[mid] < target:
left = mid + 1
else:
right = mid
return left
def upper_bound(arr, target):
left, right = 0, len(arr)
while left < right:
mid = (left + right) // 2
if arr[mid] <= target:
left = mid + 1
else:
right = mid
return left
# Example usage
arr = [1, 2, 4, 4, 5]
print("Lower Bound of 4:", lower_bound(arr, 4))
print("Upper Bound of 4:", upper_bound(arr, 4))
5. 이진 탐색의 장단점
장점
- 시간 효율성: O(log N)의 시간 복잡도를 가지며, 큰 데이터 집합에서 매우 빠르게 동작합니다.
- 구현 용이성: 간단한 논리와 코드로 구현이 가능합니다.
단점
- 정렬 필요: 배열이 정렬되어 있지 않다면, 먼저 정렬해야 하므로 O(N log N)의 추가 비용이 발생합니다.
- 유연성 부족: 이진 탐색은 선형 구조에만 적용할 수 있으며, 동적 데이터에서는 사용하기 어렵습니다.
이진 탐색은 컴퓨터 과학에서 매우 중요한 알고리즘으로, 정렬된 데이터에서의 빠른 검색이 필요한 다양한 문제에 활용됩니다.
반응형
'알고리즘' 카테고리의 다른 글
시간 복잡도 계산 완벽 가이드 (코딩테스트, 알고리즘 문제 시간복잡도 계산법, 계산 팁) (0) | 2024.12.20 |
---|---|
버킷(Bucket) 알고리즘 - 코딩테스트에서 시간을 단축하는 비법(시간복잡도, C언어,Java,Python 예시코드) (0) | 2024.12.20 |
그리디 알고리즘 (Greedy Algorithm) (0) | 2024.12.19 |
DFS(깊이 우선 탐색)와 BFS(너비 우선 탐색) 알고리즘 비교(차이점, 장단점, 예시코드, 활용도) (0) | 2024.12.19 |
DFS (깊이 우선 탐색, Depth-First Search) 알고리즘 - C언어, Java, Python 예시코드, 시간복잡도 (0) | 2024.12.19 |
댓글