本文参考书籍《图解算法》
举例说明动态规划问题
考虑一个场景:周末准备一场户外旅行,要准备一些物品,你有一个可承载8kg背包和一些物品,物品也有重量和需求值,全部物品重量超过背包承重,因此无法全部携带,如何去选取价值总量最高的物品组合呢?
| 物品名 | 重量 | 价值 |
|---|---|---|
| water | 1kg | 10 |
| food | 2kg | 8 |
| tent | 3kg | 9 |
| camera | 1kg | 6 |
| book | 1kg | 3 |
| jacket | 2kg | 5 |
一、最简单的算法如下:尝试各种可能的商品组合,并找出价值最高的组合。6件商品共有64种集合方式,时间为O(2^n),也就是随着待选物品的增多,需要计算的组合呈幂次方 增加。
代码如下
import numpy
from itertools import combinations
bag = 5 # 购物袋能承受的最大承载值
#定义重量
weight={}
weight["water"]=1
weight["book"]=1
weight["food"]=2
weight["jacket"]=2
weight["camera"]=1
weight["tent"]=3
#定义价值
worth={}
worth["water"]=10
worth["book"]=3
worth["food"]=8
worth["jacket"]=5
worth["camera"]=6
worth["tent"]=9
goods_list = ["water", "book", "food", "jacket", "camera", "tent"] # 物品列表
com_lists = list()
for i in range(1, len(goods_list)+1):
com_lists += list(combinations(goods_list, i)) # 获得所有物品的所有排列组合,非重复
best_worth = 0 # 存最佳值
for one_list in com_lists:
one_weight = 0
one_worth = 0
for goods in one_list:
one_weight += weight[goods]
one_worth += worth[goods]
if one_weight <= 5: # 当总重量小于5时,并且比best_worth值大时,取最佳值,直到遍历所有组合
if one_worth > best_worth:
best_worth = one_worth
best_com = one_list
print(best_com,best_worth)
计算结果为(‘water’, ‘book’, ‘food’, ‘camera’) 27
二、下面试一下动态规划的方法
动态规划先将背包的承载量划分为小块,第一行的记录为细分的小背包能承受的重量,竖排为物品,然后空格中填写每个小背包中能放下的物品的最大价值。当然,你只能填写本行物品和之前行的物品。
每个动态规划算法都从一个网格开始,背包问题的网格如下。
| 物品名/重量 | 1kg | 2kg | 3kg | 4kg | 5kg |
|---|---|---|---|---|---|
| water | |||||
| food | |||||
| tent | |||||
| camera | |||||
| book | |||||
| jacket |
网格最初是空的。你将填充其中的每个单元格,网格填满后,就找到了问题的答案!
water行
| 物品名/重量 | 1kg | 2kg | 3kg | 4kg | 5kg |
|---|---|---|---|---|---|
| water | 10 | 10 | 10 | 10 | 10 |
| food | |||||
| tent | |||||
| camera | |||||
| book | |||||
| jacket |
注意填入规则:在1-6kg的背包中,选择当前行或者之前行的物品,使在承载范围内的物品价值最大。
填入的原则为:
table[i][j]= max(table[i-1][j],当前商品的价值+剩余空间价值(table[i-1][j-当前商品重量]))
| 物品名/重量 | 1kg | 2kg | 3kg | 4kg | 5kg |
|---|---|---|---|---|---|
| water | 10 | 10 | 10 | 10 | 10 |
| food | 10 | 10 | 18 | 18 | 18 |
| tent | 10 | 10 | 18 | 19 | 19 |
| camera | 10 | 16 | 18 | 19 | 25 |
| book | 10 | 16 | 19 | 24 | 27 |
| jacket | 10 | 16 | 19 | 24 | 27 |
如图所示,表格的右下方数值就是5kg背包所能承载物品的最大价值,物品组合为:water,food,camera,book。

本文通过一个户外旅行的背包问题,介绍了如何使用动态规划来解决物品选取以达到最大价值的问题。对比了简单算法的时间复杂度,并详细解释了动态规划方法的步骤和填充规则,最终找到在背包承重限制下价值最高的物品组合。
8103

被折叠的 条评论
为什么被折叠?



