算法:01背包问题【动态规划】

01背包问题【动态规划】

01背包是典型的动态规划问题。

动态规划的原理

动态规划与分治法类似,都是把大问题拆分成小问题,通过寻找大问题与小问题的递推关系,解决一个个小问题,最终达到解决原问题的效果。但不同的是,分治法在子问题和子子问题等上被重复计算了很多次,而动态规划则具有记忆性,通过填写表把所有已经解决的子问题答案纪录下来,在新问题里需要用到的子问题可以直接提取,避免了重复计算,从而节约了时间,所以在问题满足最优性原理之后,用动态规划解决问题的核心就在于填表,表填写完毕,最优解也就找到。

最优性原理是动态规划的基础,最优性原理是指“多阶段决策过程的最优决策序列具有这样的性质:不论初始状态和初始决策如何,对于前面决策所造成的某一状态而言,其后各阶段的决策序列必须构成最优策略”。

01背包的状态转换方程 f[i,j] = Max{ f[i-1,j-Wi]+Pi( j >= Wi ), f[i-1,j] }

假设山洞里共有a,b,c,d ,e这5件宝物(不是5种宝物),它们的重量分别是4,5,6,2,2,它们的价值分别是6,4,5,3,6,现在给你个承重为10的背包, 怎么装背包,可以才能带走最多的财富。

有编号分别为a,b,c,d,e的五件物品,它们的重量分别是4,5,6,2,2,它们的价值分别是6,4,5,3,6,现在给你个承重为10的背包,如何让背包里装入的物品具有最大的价值总和?

name weight value 1 2 3 4 5 6 7 8 9 10
0 0 0 0 0 0 0 0 0 0 0
a 4 6 0 0 0 0 6 6 6 6 6 6 6
b 5 4 0 0 0 0 6 6 6 6 6 10 10
c 6 5 0 0 0 0 6 6 6 6 6 10 11
d 2 3 0 0 3 3 6 6 9 9 9 10 11
e 2 6 0 0 6 6 9 9 12 12 15 15 15

e8的值是如何求出来的?

根据01背包状态转换方程,需要考虑2个值:
1)f(i-1, j)
2)max( f(i-1,j), f(i-1, j-w(i)) + v(i) )
其中,
f(i-1,j)表示背包承重为j时,前i-1个能装的最大价值,本例中表示我有一个承重为8的背包,当只有物品a,b,c,d四件可选时,这个背包能装入的最大价值,即d8;
f(i-1, j-w(i)) + v(i)表示背包承重为j-w(i)时,前i-1个能装的最大价值(其中w(i)为第i个物品的重量),再加上i物品的价值v(i),在本例即为d6+6=15。

回溯求最优解组合

通过上面的方法可以求出背包问题的最优解,但还不知道这个最优解由哪些商品组成,故要根据最优解回溯找出解的组成,根据填表的原理可以有如下的寻解方式:

V(i,j)=V(i-1,j)时,说明没有选择第i 个商品,则回到V(i-1,j);
V(i,j)=V(i-1,j-w(i))+v(i)时,说明装了第i个商品,该商品是最优解组成的一部分,随后我们得回到装该商品之前,即回到V(i-1,j-w(i));
一直遍历到i=0结束为止,所有解的组成都会找到。

压缩优化

1、当前要求状态只与上一个状态有关,因此可以压缩数组维度,例如二维压缩为一维
2、压缩后数组只存储最后一件物品(即最后一行)的结果,只能得到最优解,不能求出最优解的组合
3、压缩后在列上必须倒着更新,否则会覆盖前面的。
参考1
参考2

# 01背包问题
# 输入:第一行为用例个数,第二行包含N和cap,表示物品数和背包容量,之后的N行为物品重量weight和价值value,用空格隔开
# 输出:背包能装的最大价值,若能输出路径,则输出所装的东西


def search_path(dp, arr, i, j):  # 递归求装入的物品,最优解回溯,求最优解的组成
    if i <= 0:
        return
    if dp[i][j] == dp[i-1][j]:
        search_path(dp, arr, i-1, j)
    else:
     
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值