[1]. Overlapping Subproblems(겹치는 부분 문제)
- 동일한 작은 문제를 반복적으로 해결한다.
[2]. Optimal Substructure(최적 부분 구조)
- 큰 문제를 작은 문제로 나눌 수 있고 작은 문제의 답을 모아서 다시 큰 문제를 해결한다.
dp[0]
의 상태에서 출발하는 대신 dp[n]
의 값을 찾기 위해 위에서부터 바로 호출을 시작하는데 이 때 호출을 할 때 사용하는 것이 바로 재귀다.현수는 네트워크 선을 1m, 2m의 길이를 갖는 선으로 자르려고 한다.
예를 들어, 4m의 네트워크 선이 주어진다면1) 1m + 1m + 1m + 1m
2) 2m + 1m + 1m
3) 1m + 2m + 1m
4) 1m + 1m + 2m
5) 2m + 2m의 5가지 방법을 생각할 수 있다. (2), (3), (4)의 경우 왼쪽을 기준으로 자르는 위치가 다르면 다른 경우로 생각한다. 그렇다면 네트워크 선의 길이가 Nm라면 몇 가지의 자르는 방법이 나올까?
import sys
input = sys.stdin.readline
N = int(input())
memoization = [0] * (N+1)
def func(x):
if x == 1 or x == 2:
return x
# 이미 처리된 결과라면?
if memoization[x] != 0:
return memoization[x]
memoization[x] = func(x-1) + func(x-2)
return memoization[x]
print(func(N))
import sys
input = sys.stdin.readline
N = int(input())
dp = [0] * (N+1)
dp[1] = 1
dp[2] = 2
for i in range(3, N+1):
dp[i] = dp[i-1] + dp[i-2]
print(dp[N])
[레퍼런스]
이코테 2021 - Dynamic Programming
인프런 - 파이썬 알고리즘 문제풀이 입문(코딩테스트 대비)