Python实现背包问题的两种解决方法

动态规划方法解决背包问题

# 物品重量与价值
tr = [None, {'w': 2, 'v': 3}, {'w': 3, 'v': 4},
      {'w': 4, 'v': 8}, {'w': 5, 'v': 8}, {'w': 9, 'v': 10}]
# 最大容量
max_w = 20
# 初始化二维表格
# 集合的形式作为二维表格
m = {(i, w): 0 for i in range(len(tr))
     for w in range(max_w + 1)}
for i in range(1,len(tr)):
    for w in range(1,max_w+1):
        if tr[i]['w'] > w:
            m[(i,w)] = m[(i-1,w)]
        else:
            m[(i,w)] = max(m[(i-1,w)],m[(i-1,w-tr[i]['w'])] + tr[i]['v'])
print(type(m))
print(m[(len(tr)-1,max_w)])

递归方法解决背包问题

# 货物重量
# 集合的形式存放
tr = {(2,3),(3,4),(4,8),(5,8),(9,10)}
# 最大载重
max_w = 20
# 初始化记忆表格m
# key是(宝物组合,最大重量),value是最大价值
m={}

def thief(tr,w):
    if tr == set() or w == 0:
        m[(tuple(tr),w)] = 0 #tuple是key的要求
        return 0
    elif(tuple(tr),w) in m:
        return m[(tuple(tr),w)]
    else:
        vmax = 0
        for t in tr:
            if t[0] <= w:
                # 逐个从集合中去掉某个宝物,递归调用
                # 选出所有价值中最大的值
                v = thief(tr-{t}, w-t[0]) + t[1]
                vmax = max(vmax,v)
        m[(tuple(tr),w)] = vmax
        return vmax

print(thief(tr,max_w))

  有两点心得,递归更像是不断地剥洋葱,一层一层地剥开,这里面要循环调用自定义函数求解更小规模的子问题。
  而动态规划这类问题,要首先在脑海中构造一个表格,这里用到的是一个二维表格,然后有一点必须要记得:动态规划当中地任意一个状态只和前一个状态有关,而与之前状态无关。所以把这个表格填满之后就可以得到动态规划问题的最优解。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值