1 λΆ„ μ†Œμš”

동적 κ³„νšλ²•(Dynamic Programming)μ΄λž€?

동적 κ³„νšλ²•μ€ 큰 문제λ₯Ό μž‘μ€ 문제둜 λ‚˜λˆ„μ–΄ ν‘ΈλŠ” 문제λ₯Ό λ§ν•œλ‹€.
큰 문제λ₯Ό μž‘μ€ 문제둜 λ‚˜λˆ„λŠ” 것은 λΆ„ν•  정볡(Divide and Conquer)와 λΉ„μŠ·ν•΄λ³΄μΈλ‹€. ν•˜μ§€λ§Œ 결정적인 차이점이 μžˆλŠ”λ°, λ°”λ‘œ μž‘μ€ λ¬Έμ œκ°€ 쀑볡이 μΌμ–΄λ‚˜λŠ”μ§€ μΌμ–΄λ‚˜μ§€ μ•ŠλŠ”μ§€μ΄λ‹€.

λΆ„ν•  정볡은 큰 문제λ₯Ό ν•΄κ²°ν•˜κΈ° μ–΄λ €μ›Œ μž‘μ€ 문제둜 λ‚˜λˆ„μ–΄ ν‘ΈλŠ” 방식이닀. νŠΉμ§•μ€ μž‘μ€ λ¬Έμ œμ—μ„œ 반볡이 μΌμ–΄λ‚˜μ§€ μ•ŠλŠ”λ‹€λŠ” 점이닀.
동적 κ³„νšλ²•μ€ μž‘μ€ λ¬Έμ œλ“€μ΄ λ°˜λ³΅λ˜λŠ” 것이 νŠΉμ§•μ΄λ©°, 이λ₯Ό μ΄μš©ν•΄ ν’€μ–΄λ‚˜κ°€λŠ” 방식이닀.

동적 κ³„νšλ²• 방법

동적 κ³„νšλ²•μœΌλ‘œ 문제λ₯Ό ν‘ΈλŠ” 방법은 λͺ¨λ“  μž‘μ€ λ¬Έμ œλ“€μ„ ν•œ 번만 ν‘ΈλŠ” 것이닀.
정닡을 κ΅¬ν•œ μž‘μ€ λ¬Έμ œλ“€μ„ μ–΄λ”˜κ°€μ— λ©”λͺ¨(Momoization)ν•΄λ†“μ•˜λ‹€κ°€, 같은 상황이 λ°œμƒν•˜λ©΄ κ·Έ 결과값을 μ‚¬μš©ν•œλ‹€.

동적 κ³„νšλ²•μ˜ 쑰건?

동적 κ³„νšλ²•μ„ μ‚¬μš©ν•˜λŠ” 쑰건은 λ‹€μŒκ³Ό κ°™λ‹€.

  1. μž‘μ€ λ¬Έμ œκ°€ 반볡이 μΌμ–΄λ‚˜λŠ” 경우
  2. 같은 λ¬Έμ œλŠ” ꡬ할 λ•Œλ§ˆλ‹€ 정닡이 κ°™μ•„μ•Ό 함

μ΄λŸ¬ν•œ 쑰건을 λ§Œμ‘±ν•˜λŠ” 경우만 동적 κ³„νšλ²•μ„ μ‚¬μš©ν•  수 μžˆλ‹€.

동적 κ³„νšλ²• μš”μ•½ - μž₯점

  1. λ©”λͺ¨λ¦¬λ₯Ό μ‚¬μš©ν•΄μ„œ 쀑볡 연산을 μ€„μž„
  2. 쀑볡 연산을 μ€„μ—¬μ„œ μˆ˜ν–‰ 속도λ₯Ό κ°œμ„ ν•¨

μ˜ˆμ‹œ - ν”Όλ³΄λ‚˜μΉ˜ μˆ˜μ—΄

ν”Όλ³΄λ‚˜μΉ˜ μˆ˜μ—΄μ€ F(n) = F(n-1) + F(n-2)의 점화식을 κ°–λŠ” μˆœμ—΄μ΄λ‹€. 이 λ¬Έμ œλŠ” μž¬κ·€ ν•¨μˆ˜λ₯Ό 톡해 ν•΄κ²°ν•  수 μžˆμ§€λ§Œ, n이 증가함에 따라 ν˜ΈμΆœλ˜λŠ” ν•¨μˆ˜μ˜ μˆ˜κ°€ κΈ°ν•˜κΈ‰μˆ˜μ μœΌλ‘œ μ¦κ°€ν•˜κΈ° λ•Œλ¬Έμ— 일정 수 μ΄μƒμ˜ μˆœμ—΄μ„ κ΅¬ν•˜κΈ° μ–΄λ ΅λ‹€.

μž¬κ·€ν•¨μˆ˜ μ‚¬μš©

def fub(n):
    if n <= 1:
        return n
    else:
        return fib(n-1) + fib(n-2)


이 문제λ₯Ό 동적 κ³„νšλ²•(DP)λ₯Ό μ‚¬μš©ν•΄ μ ‘κ·Όν•΄λ³΄μž.

  1. μž‘μ€ λ¬Έμ œλ“€μ΄ λ°˜λ³΅λœλ‹€.
    예λ₯Ό λ“€μ–΄ F(5) = F(4) + F(3), F(4) = F(3) - F(2) 인데, μ—¬κΈ°μ„œ F(3)이 λ°˜λ³΅λ˜λŠ” 것을 λ³Ό 수 μžˆλ‹€. 즉, μž‘μ€ λ¬Έμ œκ°€ 반볡되고 μžˆλ‹€λŠ” λœ»μ΄λ‹€.

  2. 같은 λ¬Έμ œλŠ” ꡬ할 λ•Œλ§ˆλ‹€ 정닡이 κ°™λ‹€.
    ν”Όλ³΄λ‚˜μΉ˜ μˆ˜μ—΄μ€ F(1)κ³Ό F(2)의 값은 λͺ¨λ‘ 1둜 κ³ μ •λ˜μ–΄ μžˆλ‹€.
    즉, 3번째 μˆ˜μ—΄μ€ μ–Έμ œλ‚˜ 결과값이 2이고, 4번째 μˆ˜μ—΄μ€ 2 + 1μ΄λ―€λ‘œ μ–Έμ œλ“  결과값이 κ°™λ‹€.

ν”Όλ³΄λ‚˜μΉ˜ μˆ˜μ—΄ DP

def fibo(n):
    dp[0] = 1
    dp[1] = 1
    
    if n < 2:
        return dp[n]
    for i in range(2, n+1):
        dp[i] = dp[i-2] + dp[i-1]
    
    return dp[n]

참고자료

https://galid1.tistory.com/507
https://www.youtube.com/watch?v=0bqfTzpWySY&t=423s

νƒœκ·Έ:

μΉ΄ν…Œκ³ λ¦¬:

μ—…λ°μ΄νŠΈ:

λŒ“κΈ€λ‚¨κΈ°κΈ°