
분할 정복(Divide and Conquer)은 복잡한 문제를 작은 부분 문제로 나누어 해결한 뒤,
이를 다시 합쳐 원래 문제의 해답을 얻는 알고리즘 설계 기법이다.쉽게 말해, "문제를 작게 나누고, 각 문제를 해결한 뒤, 그 결과를 합쳐서 큰 문제를 해결하는 방식"
분할 정복 알고리즘은 보통 다음 세 단계로 구성된다.
| 알고리즘 | 설명 | 시간복잡도 |
|---|---|---|
| 병합 정렬 (Merge Sort) | 배열을 반씩 나누어 정렬하고 병합하는 알고리즘 | |
| 퀵 정렬 (Quick Sort) | 피벗을 기준으로 나누어 정렬하는 알고리즘 | 평균 , 최악 |
| 이진 탐색 (Binary Search) | 정렬된 데이터에서 값을 빠르게 찾는 알고리즘 | |
| 거듭제곱 (Fast Power) | 빠르게 제곱수를 계산하는 알고리즘 | |
| 스트라센 알고리즘 | 행렬 곱셈을 더 빠르게 계산하는 알고리즘 | 약 |
분할 정복 알고리즘의 일반적인 시간 복잡도는 다음과 같이 표현된다.
병합 정렬의 경우
거듭제곱은 단순히 a^n을 반복 곱셈으로 구하면 의 시간이 걸린다.
하지만 분할 정복을 사용하면 시간에 빠르게 계산할 수 있다.
def fast_power(a, n):
if n == 0:
return 1
half = fast_power(a, n // 2)
if n % 2 == 0:
return half * half
else:
return a * half * half
# 예시: 2^10 = 1024
print(fast_power(2, 10)) # 출력: 1024
큰 수를 계산할 때는 중간에 모듈러 연산을 적용해 오버플로우를 방지하고 효율적으로 계산할 수 있다.
def fast_power_mod(a, n, mod):
if n == 0:
return 1
half = fast_power_mod(a, n // 2, mod)
result = (half * half) % mod
if n % 2 == 1:
result = (result * a) % mod
return result
# 예시: 2^10 % 1000 = 24
print(fast_power_mod(2, 10, 1000)) # 출력: 24
import time
# 비교용 큰 수
a = 987654321
n = 10**9
mod = 1_000_000_007
# 사용자 정의 함수 시간 측정
start = time.time()
custom_result = fast_power_mod(a, n, mod)
end = time.time()
print(f"Custom fast_power_mod result: {custom_result}")
print(f"Custom function time: {end - start:.6f} seconds")
# 내장 함수 pow 시간 측정
start = time.time()
builtin_result = pow(a, n, mod)
end = time.time()
print(f"Built-in pow result: {builtin_result}")
print(f"Built-in pow time: {end - start:.6f} seconds")
# 결과
Custom fast_power_mod result: 69424128
Custom function time: 0.000118 seconds
Built-in pow result: 69424128
Built-in pow time: 0.000005 seconds
내장 함수 pow(a, b, mod)는 C로 작성되어 있고 파이썬 인터프리터 수준에서 최적화되어 있기 때문에 매우 빠르다.
반면, fast_power_mod는 Python으로 작성된 재귀 함수이므로 약간의 오버헤드가 있지만, 그럼에도 불구하고 충분히 빠른 속도를 보여준다.