카테고리 없음
동적 계획법
sck07013
2024. 10. 1. 18:51
동적 계획법의 핵심 개념
- 최적 부분 구조 (Optimal Substructure):
- 문제를 더 작은 하위 문제로 나눌 수 있으며, 하위 문제의 최적 해답을 사용하여 원래 문제의 최적 해답을 구할 수 있음
- 중복되는 부분 문제 (Overlapping Subproblems):
- 동일한 하위 문제가 여러 번 반복해서 계산됩니다. 이를 해결하기 위해 하위 문제의 해답을 저장하고 재사용
동적 계획법의 두 가지 접근 방식
- 상향식 접근법 (Bottom-Up Approach):
- 작은 하위 문제부터 해결해 나가면서, 최종적으로 원래 문제를 해결
- 일반적으로 테이블을 사용하여 하위 문제의 해답을 저장
- 하향식 접근법 (Top-Down Approach):
- 문제를 더 작은 하위 문제로 재귀적으로 분할하여 해결
- 메모이제이션 기법을 사용하여 이미 계산된 하위 문제의 해답을 저장하고 재사용
#동적 계획법
동적 계획법의 개념
불필요한 연산을 줄이고 최적의 답안을 구하는 알고리즘
#이차원 표 구성과 초기화
배열 = [[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0]]
또는
배열 = [[0 for _ in range(8)] for _ in range(5)]
if (금괴무게 > 현재배낭무게)
배열[행][열] = 배열[행-1][열]
# 클래스와 함수 선언 부분
def knapsack(maxWeight, rowCount, weight, money):
print('##메모제이션 배열##')
array = [[0 for _ in range(maxWeight+1)] for _ in range(rowCount+1)]
for row in range(1, rowCount+1):
print(row, '개 -->', end=' ')
for col in range(1, maxWeight+1):
if weight[row-1] > col:
array[row][col] = array[row-1][col]
else:
value1 = money[row-1] + array[row-1][col-weight[row-1]]
value2 = array[row-1][col]
array[row][col] = max(value1, value2)
print('%2d' % array[row][col], end=' ')
print()
return array[rowCount][maxWeight]
# 전역 변수 선언 부분
maxWeight = 7
rowCount = 4
weight = [6, 4, 3, 5]
money = [13, 8, 6, 12]
# 메인 코드 부분
print('배낭에 담을 수 있는 최대 가치:', knapsack(maxWeight, rowCount, weight, money))
##메모제이션 배열##
1 개 --> 0 0 0 0 0 13 13
2 개 --> 0 0 0 8 8 13 13
3 개 --> 0 0 6 8 8 13 14
4 개 --> 0 0 6 8 12 13 14
배낭에 담을 수 있는 최대 가치: 14
##동적 계획법 활용
#클래스와 함수 선언 부분
def growRich() :
memo = [[0 for _ in range(COL)] for _ in range(ROW)]
memo[0][0] = goldMaze[0][0]
rowSum = memo[0][0]
for i in range(1, ROW) :
rowSum += goldMaze[0][i]
memo[0][i] = rowSum
colSum = memo[0][0]
for i in range(1, COL) :
colSum += goldMaze[i][0]
memo[i][0] = colSum
for row in range(1, ROW) :
for col in range(1, COL) :
if (memo[row][col-1] > memo[row-1][col]) :
memo[row][col] = memo[row][col-1] + goldMaze[row][col]
else :
memo[row][col] = memo[row-1][col] + goldMaze[row][col]
return memo[ROW-1][COL-1]
#전역 변수 선언 부분
ROW, COL = 5, 5
goldMaze = [[1, 4, 4, 2, 2],
[1, 3, 3, 0, 5],
[1, 2, 4, 3, 0],
[3, 3, 0, 4, 2],
[1, 3, 4, 5, 3]]
#메인 코드 부분
macolGold = growRich()
print('황금 미로에서 얻은 최대 황금 개수 -->', macolGold)
황금 미로에서 얻은 최대 황금 개수 --> 31