Ch8 Dynamic Programing 8-1
๐ ๋์ ํ๋ก๊ทธ๋ ๋ฐ (Dynamic Programing) ์๊ณ ๋ฆฌ์ฆ
๋์ ํ๋ก๊ทธ๋๋ฐ (Dynamic Programing) ์ด๋ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ์ ์ ํ ์ฌ์ฉํ์ฌ ์ํ ์๊ฐ ํจ์จ์ฑ์ ๋น์ฝ์ ์ผ๋ก ํฅ์์ํค๋ ๋ฐฉ๋ฒ.
- ์ด๋ฏธ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ(์์ ๋ฌธ์ )๋ ๋ณ๋์ ๋ฉ๋ชจ๋ฆฌ ์์ญ์ ์ ์ฅํ์ฌ ๋ค์ ๊ณ์ฐํ์ง ์๋๋ก ํจ.
- ๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ์ ๊ตฌํ์ ์ผ๋ฐ์ ์ผ๋ก ๋ ๊ฐ์ง ๋ฐฉ์(ํ๋ค์ด๊ณผ ๋ณดํ ์ )์ผ๋ก ๊ตฌ์ฑ.
- ๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ์ ๋์ ๊ณํ๋ฒ์ด๋ผ๊ณ ๋ ๋ถ๋ฆ.
- DP๋ ๋ค์์ ์กฐ๊ฑด์ ๋ง์กฑํ ๋ ์ฌ์ฉํ ์ ์๋ค.
- ์ต์ ๋ถ๋ถ ๊ตฌ์กฐ (Optimal Substructure)
- ํฐ ๋ฌธ์ ๋ฅผ ์์ ๋ฌธ์ ๋ก ๋๋ฃจ ์ ์์ผ๋ฉฐ ์์ ๋ฌธ์ ์ ๋ต์ ํฐ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ ์ ์๋ค.
- ์ค๋ณต๋๋ ๋ถ๋ถ ๋ฌธ์ (Overlapping Subproblem)
- ๋์ผํ ์์ ๋ฌธ์ ๋ฅผ ๋ฐ๋ณต์ ์ผ๋ก ํด๊ฒฐํด์ผ ํ๋ค.
- ์ต์ ๋ถ๋ถ ๊ตฌ์กฐ (Optimal Substructure)
๋์ (Dynamic)์ด๋
- ์๋ฃ๊ตฌ์กฐ์์ ๋์ ํ ๋น(Dynamic Allocation)์ โํ๋ก๊ทธ๋จ์ด ์คํ๋๋ ๋์ค์ ์คํ์ ํ์ํ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ํ ๋นํ๋ ๊ธฐ๋ฒโ์ ์๋ฏธํฉ๋๋ค
- ๋ฐ๋ฉด์ ๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ์์ โ๋ค์ด๋๋ฏนโ์ ๋ณ๋ค๋ฅธ ์๋ฏธ ์์ด ์ฌ์ฉ๋ ๋จ์ด์ด๋ค
๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ์ผ๋ก ํด๊ฒฐํ ์ ์๋ ๋ํ์ ์ธ ์์๋ก ํผ๋ณด๋์น ์์ด์ด ์๋ค.
ํผ๋ณด๋์น ์์ด
- ํผ๋ณด๋์น ์์ด์ด๋ ์ด์ ๋ํญ์ ํฉ์ ํ์ฌ์ ํญ์ผ๋ก ์ค์ ํ๋ ํน์ง์ด ์๋ ์์ด์ด๋ค. ํผ๋ณด๋์น ์์ด์ ๋ค์๊ณผ ๊ฐ์ ํํ๋ก ๋์์ด ์ด์ด์ง๋ค.
- ์ ํ์์ ์ฌ์ฉํด ํผ๋ณด๋์น ์์ด์ ๊ฐ๊ฒฐํ๊ฒ ํํ์ด ๊ฐ๋ฅํ๋ค.
- ํผ๋ณด๋์น ์์ด์ ์ ํ์์ ๋ค์๊ณผ ๊ฐ๋ค.
- a(n) = a(n-1) + a(n-2)
- n ๋ฒ์งธ ํผ๋ณด๋์น ์ = (n-1)๋ฒ์งธ ํผ๋ณด๋์น ์ + (n-2)๋ฒ์งธ ํผ๋ณด๋์น ์
- a(1) = 1, a(2) = 2
- ๋จ, 1๋ฒ์งธ ํผ๋ณด๋์น ์ = 1, 2๋ฒ์งธ ํผ๋ณด๋์น ์ = 1
- a(n) = a(n-1) + a(n-2)
- ํ๋ก๊ทธ๋๋ฐ ์์๋ ์ด๋ฌํ ์์ด์ ๋ฐฐ์ด์ด๋ ๋ฆฌ์คํธ๋ก ํํํ ์ ์๋ค.
- ์ํ์ ์ ํ์์ ํ๋ก๊ทธ๋๋ฐ์ผ๋ก ํํํ๋ ค๋ฉด ์ฌ๊ท ํจ์๋ฅผ ์ฌ์ฉํ๋ฉด ๊ฐ๋จํ๋ค.
# ํผ๋ณด๋์น ํจ์๋ฅผ ๋จ์ ์ฌ๊ท ํจ์๋ก ํํ
def fibo(x):
if x==1 or x==2:
return 1
return fibo(x-1) + fibo(x-2)
print(fibo(4))
ํผ๋ณด๋์น ์์ด์ ์๊ฐ๋ณต์ก๋ ๋ถ์
- f(n)์์ n์ด ์ปค์ง์๋ก ํธ์ถ ์๊ฐ ๋ง์์ง๋ฏ๋ก ์ข์ง์์ ์ฝ๋์ด๋ค.
- ํผ๋ณด๋์น ์์ด์ ์๊ฐ ๋ณต์ก๋๋ ๋ค์๊ณผ ๊ฐ์.
- ์ธํ ํ๊ธฐ๋ฒ: ๐(1.618โฏแดบ)
- ๋น ์ค ํ๊ธฐ๋ฒ: O(2แดบ)
- ๋น ์ค ํ๊ธฐ๋ฒ์ ๊ธฐ์ค์ผ๋ก f(30)์ ๊ณ์ฐํ๊ธฐ ์ํด ์ฝ 10์ต๊ฐ๋์ ์ฐ์ฐ์ ์ํํด์ผ ํจ.
ํผ๋ณด๋์น ์์ด ํจ์จ์ ์ธ ํด๋ฒ: DP
- ๋ค์ ์กฐ๊ฑด์ ๋ง์กฑํ ๋ DP๋ฅผ ์ฌ์ฉํ ์ ์๋ค.
- ํฐ ๋ฌธ์ ๋ฅผ ์์ ๋ฌธ์ ๋ก ๋๋ ์ ์๋ค.
- ์์ ๋ฌธ์ ์์ ๊ตฌํ ์ ๋ต์ ๊ทธ๊ฒ์ ํฌํจํ๋ ํฐ ๋ฌธ์ ์์๋ ๋์ผํ๋ค.
- ๋ฉ๋ชจ์ ์ด์
๊ธฐ๋ฒ์ ์ฌ์ฉํด์ ํด๊ฒฐ์ด ๊ฐ๋ฅํ๋ค.
- ๋ฉ๋ชจ์ด์ ์ด์ ์ ๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ์ ๊ตฌํํ๋ ๋ฐฉ๋ฒ ์ค ํ ์ข ๋ฅ.
- ํ ๋ฒ ๊ตฌํ ๊ฒฐ๊ณผ๋ฅผ ๋ฉ๋ชจ๋ฆฌ ๊ณต๊ฐ์ ๋ฉ๋ชจํ๋ ๊ธฐ๋ฒ.
- ๊ฐ์ ์์ ๋ค์ ํธ์ถํ๋ฉด ๋ฉ๋ชจํ ๊ฒฐ๊ณผ๋ฅผ ๊ทธ๋๋ก ๊ฐ์ ธ์ค๋ ๊ธฐ๋ฒ.
- ๊ฐ์ ๊ธฐ๋กํด ๋๋๋ค๋ ์ ์์ ์บ์ฑ(Cashing)์ด๋ผ๊ณ ๋ ํ๋ค.
- ๊ตฌํ์ ๋จ์ํ๊ฒ ํ๋ฒ ๊ตฌํ ์ ๋ณด๋ฅผ ๋ฆฌ์คํธ์ ์ ์ฅํ๋ ๊ฒ์ด๋ค.
ํ๋ค์ด VS ๋ณดํ ์
- ํ๋ค์ด(๋ฉ๋ชจ์ ์ด์ ) ๋ฐฉ์์ ํํฅ์์ด๋ผ๊ณ ๋ ํ๋ฉฐ ๋ณดํ ์ ๋ฐฉ์์ ์ํฅ์์ด๋ผ๊ณ ๋ ํ๋ค.
- DP์ ์ ํ์ ์ธ ํํ๋ ๋ณดํ
์
๋ฐฉ์์ด๋ค.
- ๊ฒฐ๊ณผ ์ ์ฅ์ฉ ๋ฆฌ์คํธ๋ DP ํ ์ด๋ธ์ด๋ผ๊ณ ๋ถ๋ฅธ๋ค.
- ๋ฉ๋ชจ์ ์ด์
์ ์ด์ ์ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ์ผ์์ ์ผ๋ก ๊ธฐ๋กํด ๋์ ๋์ ๊ฐ๋
์ ์๋ฏธํ๋ค.
- ๋ฐ๋ผ์ ๋ฉ๋ชจ์ ์ด์ ์ DP์ ๊ตญํ๋ ๊ฐ๋ ์ด ์๋๋ค.
- ํ ๋ฒ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ๋ด์ ๋๊ธฐ๋ง ํ๊ณ DP๋ฅผ ์ํด ํ์ฉํ์ง ์์ ์๋ ์๋ค.
# ํผ๋ณด๋์น ์์ด: ํ๋ค์ด DP ์์ค์ฝ๋
# ํ ๋ฒ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ๋ฉ๋ชจ์ด์ ์ด์
(Memoization)ํ๊ธฐ ์ํ ๋ฆฌ์คํธ ์ด๊ธฐํ
d = [0] * 100
# ํผ๋ณด๋์น ํจ์(Fibonacci Function)๋ฅผ ์ฌ๊ทํจ์๋ก ๊ตฌํ(ํ๋ค์ด DP)
def fibo(x):
# ์ข
๋ฃ ์กฐ๊ฑด(1 ํน์ 2์ผ ๋ 1์ ๋ฐํ)
if x == 1 or x == 2:
return 1
# ์ด๋ฏธ ๊ณ์ฐํ ์ ์๋ ๋ฌธ์ ๋ผ๋ฉด ๊ทธ๋๋ก ๋ฐํ
if d[x] != 0:
return d[x]
# ์์ง ๊ณ์ฐํ์ง ์์ ๋ฌธ์ ๋ผ๋ฉด ์ ํ์์ ๋ฐ๋ผ์ ํผ๋ณด๋์น ๊ฒฐ๊ณผ ๋ฐํ
d[x] = fibo(x - 1) + fibo(x - 2)
return d[x]
print(fibo(99))
>>> 218922995834555169026
# ํผ๋ณด๋์น ์์ด: ๋ณดํ
์
DP ์์ค์ฝ๋
# ์์ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ์ ์ฅํ๊ธฐ ์ํ DP ํ
์ด๋ธ ์ด๊ธฐํ
d = [0] * 100
# ์ฒซ๋ฒ์งธ ํผ๋ณด๋์น ์์ ๋๋ฒ์งธ ํผ๋ณด๋์น ์๋ 1
d[1] = 1
d[2] = 2
n = 99
# ํผ๋ณด๋์น ํจ์(Fibonacci Function) ๋ฐ๋ณต๋ฌธ์ผ๋ก ๊ตฌํ(๋ณดํ
์
DP)
for i in range(3, n + 1):
d[i] = d[i - 1] + d[i - 2]
print(d[n])
>>> 218922995834555169026
ํผ๋ณด๋์น ์์ด: ๋ฉ๋ชจ์ ์ด์ ๋์ ๋ถ์
์ด๋ฏธ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ๋ฉ๋ชจ๋ฆฌ์ ์ ์ฅํ์ฌ ๋ค์๊ณผ ๊ฐ์ด ์์น ๋ ๋ ธ๋๋ง ์ฒ๋ฆฌํ ๊ฒ์ ๊ธฐ๋ ํ ์ ์๋ค.
์ค์ ๋ก ํธ์ถ๋๋ ํจ์๋ ์์น ๋ ํจ์๋ง ํธ์ถ๋๋ค.
- ๋ฉ๋ชจ์ด์ ์ด์ ์ ์ด์ฉํ๋ ๊ฒฝ์ฐ ์๊ฐ ๋ณต์ก๋๋ O(N)
ํผ๋ณด๋์น ์์ค์ฝ๋(ํ๋ค์ด)
- ์ฌ๊ท ํจ์๋ฅผ ์ด์ฉํ์ฌ ํฐ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ๊ธฐ ์ํด ์์ ๋ฌธ์ ๋ฅผ ํธ์ถํ๋ ๊ฒฝ์ฐ
d = [0] * 100
def fibo(x):
print('f(' + str(x) + ')', end=' ')
if x == 1 or x == 2:
return 1
if d[x] != 0:
return d[x]
d[x] = fibo(x - 1) + fibo(x - 2)
return d[x]
fibo(6)
>>>> f(6) f(5) f(4) f(3) f(2) f(1) f(2) f(3) f(4)
ํผ๋ณด๋์น ์์ค์ฝ๋(๋ณดํ ์ )
- ๋์ผํ ์๋ฆฌ๋ฅผ ์ ์ฉํ๋ ๋จ์ํ ๋ฐ๋ณต๋ฌธ์ ์ด์ฉํ์ฌ ์์ ๋ฌธ์ ๋ถํฐ ๋ฌธ์ ๋ฅผ ํด๊ฒฐ
# ์์ ๊ณ์ฐ๋ ๊ฒฐ๊ณผ๋ฅผ ์ ์ฅํ๊ธฐ ์ํ DP ํ
์ด๋ธ ์ด๊ธฐํ
d = [0] * 100
# ์ฒซ ๋ฒ์งธ ํผ๋ณด๋์น ์์ ๋ ๋ฒ์งธ ํผ๋ณด๋์น ์๋ 1
d[1] = 1
d[2] = 1
n = 99
# ํผ๋ณด๋์น ํจ์ ๋ฐ๋ณต๋ฌธ์ผ๋ก ๊ตฌํ(bottom-up)
for i in range(3, n+1):
d[i] = d[i-1] + d[i-2]
print(d[n])
๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ VS ๋ถํ ์ ๋ณต
- ์ด๋ฌํ ํฐ ๋ฌธ์ ๋ฅผ ์๊ฒ ๋๋๋ ๋ฐฉ๋ฒ์ ํต ์ ๋ ฌ์์๋ ์๊ฐ๋ ์ ์ด ์๋ค.
- ํต ์ ๋ ฌ์ ์ ๋ ฌ์ ์ํํ ๋ ์ ๋ ฌํ ๋ฆฌ์คํธ๋ฅผ ๋ถํ ํ์ฌ ์ ์ฒด์ ์ผ๋ก ์ ๋ ฌ์ด ๋ ์ ์๋๋ก ํ๋ค. ์ด๋ ๋ถํ ์ ๋ณต ์๊ณ ๋ฆฌ์ฆ์ผ๋ก ๋ถ๋ฅ๋๋ค. ->ํต์ ๋ ฌ ๋ถํ ์ ๋ณต
- DP์ ๋ถํ ์ ๋ณต์ ๋ชจ๋ ์ต์ ๋ถ๋ถ ๊ตฌ์กฐ๋ฅผ ๊ฐ์ง ๋ ์ฌ์ฉํ ์ ์๋ค.
- ํฐ ๋ฌธ์ ๋ฅผ ์์ ๋ฌธ์ ๋ก ๋๋ ์ ์์ผ๋ฉฐ ์์ ๋ฌธ์ ์ ๋ต์ ๋ชจ์์ ํฐ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ ์ ์๋ ์ํฉ
- DP์ ๋ถํ ์ ๋ณต์ ์ฐจ์ด์ ์ ๋ถ๋ถ ๋ฌธ์ ์ ์ค๋ณต์ด๋ค.
- DP ๋ฌธ์ ์์๋ ๊ฐ ๋ถ๋ถ ๋ฌธ์ ๋ค์ด ์๋ก ์ํฅ์ ๋ฏธ์น๋ฉฐ ๋ถ๋ถ ๋ฌธ์ ๊ฐ ์ค๋ณต๋๋ค.
- ๋ถํ ์ ๋ณต ๋ฌธ์ ์์๋ ๋์ผํ ๋ถ๋ถ ๋ฌธ์ ๊ฐ ๋ฐ๋ณต์ ์ผ๋ก ๊ณ์ฐ๋์ง ์๋๋ค.
๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ ๋ฌธ์ ์ ์ ๊ทผํ๋ ๋ฐฉ๋ฒ
- ๊ฐ์ฅ ๋จผ์ ๊ทธ๋ฆฌ๋, ๊ตฌํ ์์ ํ์ ๋ฑ์ ์์ด๋์ด๋ก ๊ฐ๋ฅํ์ง ๊ฒํ ํ ์ ์๋ค.
- ๋ค๋ฅธ ์๊ณ ๋ฆฌ์ฆ์ผ๋ก ํ์ด ๋ฐฉ๋ฒ์ด ๋ ์ค๋ฅด์ง ์์ผ๋ฉด DP๋ฅผ ๊ณ ๋ คํ๋ค.
- ์ฌ๊ท ํจ์๋ก ๋นํจ์จ์ ์ธ ์์ ํ์ ํ๋ก๊ทธ๋จ์ ์์ฑํ ๋ค์ (ํ๋ค์ด) ์์ ๋ฌธ์ ์์ ๊ตฌํ ๋ต์ด ํฐ ๋ฌธ์ ์์ ๊ทธ๋๋ก ์ฌ์ฉ๋ ์ ์์ผ๋ฉด, ์ฆ ๋ฉ๋ชจ์ ์ด์ ์ ์ ์ฉํ ์ ์์ผ๋ฉด ์ฝ๋๋ฅผ ๊ฐ์ ํ๋ ๋ฐฉ๋ฒ์ ์ฌ์ฉํ ์ ์๋ค.
- ๊ฐ๋ฅํ๋ค๋ฉด ์ฌ๊ท ํจ์๋ฅผ ์ด์ฉํ๋ ํ๋ค์ด ๋ฐฉ์ ๋ณด๋ค๋ ๋ฐ๋ณต์ ์ด์ฉํ ๋ณดํ
์
๋ฐฉ์์ผ๋ก ๊ตฌํํ๋๊ฒ์ ๊ถ์ฅํ๋ค.
- ์์คํ ์ ์ฌ๊ท ํจ์์ ์คํ ํฌ๊ธฐ๊ฐ ํ์ ๋์ด ์์ ์ ์๊ธฐ ๋๋ฌธ.
- ์ผ๋ฐ์ ์ธ ์ฝ๋ฉ ํ ์คํธ ์์ค์์๋ ๊ธฐ๋ณธ ์ ํ์ DP๋ฌธ์ ๊ฐ ์ถ์ ๋๋ ๊ฒฝ์ฐ๊ฐ ๋ง๋ค.
๋๊ธ๋จ๊ธฐ๊ธฐ