1.背包问题
音响 | 3000元 | 4斤 |
笔记本电脑 | 2000元 | 3斤 |
吉他 | 1500元 | 1斤 |
1.简单算法
最简单的算法:尝试各种可能的商品组合,并找出价值最高的组合。
缺点:速度非常慢。3种商品需要计算8种组合;4件商品是,需要计算16中组合。每增加一种商品,需要计算的集合数将翻倍。这种算法的运行时间为O(2n)
组合1 | 组合2 | 组合3 | 组合4 |
无 | 吉他 | 音响 | 笔记本电脑 |
0 | 1500 | 3000 | 2000 |
组合5 | 组合6 | 组合7 | 组合8 |
吉他和音响 | 吉他和笔记本电脑 | 音响和笔记本电脑 | 吉他、音响和笔记本电脑 |
装不下 | 3500 | 装不下 | 装不下 |
近似算法可以得到近似解,但不一定是最优解。
2. 动态规划
使用动态规划可以得到最优解。
背包的承重为1斤 | 背包的承重为2斤 | 背包的承重为3斤 | 背包的承重为4斤 | |
吉他1 1500 | 可以放入背包 G 1500 | 可以放入背包 G 1500 | 可以放入背包 G 1500 | 可以放入背包 G 1500 |
音响4 3000 | G 1500 | G 1500 | G 1500 | S 3000 |
笔记本电脑3 2000 | G 1500 | G 1500 | C 2000 | 3000 vs (2000+1500) -> 3500 |
计算公式:
cell[i][j] = cell[i-1][j] vs {当前商品的价值 + 剩余空间的价值 = 当前商品的价值+cell[i-1][j-当前商品的重量]}
实现
bag={ "computer":{"weight":3,"value":2000}, "guitar":{"weight":1,"value":1500}, "sound":{"weight":4,"value":3000} } list=[] goods = [] row=0 def addList(list1,list2): for i in list1: list2.append(i) for key in bag.keys(): sublist=[] subGood=[] keyWeight = bag.get(key)["weight"] keyValue = bag.get(key)["value"] for column in range(4): sub=[] #单元格 = 列的索引+1 weight = column + 1 #判断行,行数=0,直接对比;行数大于0,与上一行进行对比 if(row > 0): if(weight < keyWeight): sublist.append(list[row-1][column]) addList(goods[row - 1][column], sub) elif(weight == bag.get(key)["weight"]): if( list[row-1][column] < keyValue ): sublist.append(keyValue) sub.append(key) else: sublist.append(list[row-1][column]) addList(goods[row-1][column],sub) else: #如果单元格重量>商品,就判断商品的权重和同位置大小 #判断weight-bag.get(key)["weight"] if (list[row-1][column] < ( keyValue + list[row-1][weight-keyWeight-1] ) ): sublist.append( keyValue + list[row-1][weight-keyWeight-1]) sub.append(key) addList(goods[row - 1][weight-keyWeight-1], sub) else: sublist.append(list[row-1][column]) addList(goods[row-1][column],sub) else: #直接判断,单元格 < 物品重量 if(weight < keyWeight): sublist.append(0) # sub.append([]) else: sublist.append(keyValue) sub.append(key) subGood.append(sub) list.append(sublist) goods.append(subGood) row+=1 #最大值肯定在最后一组,获取最大值的索引 print("4斤背包容纳的最大价值组合:%s %s" % (list[-1][max_index],goods[-1][max_index])) #4斤背包容纳的最大价值组合:3500 ['guitar', 'computer']
来源:https://www.cnblogs.com/csj2018/p/12173574.html