小记录42

87 阅读2分钟

01背包

典型动态规划问题了,背包有个capacity,然后有几个物品,有不同重量和价值。

动态规划的状态可以由两位降低到两个滚动数组,再降低到一维

首先是两维:

一维i代表当前遍历到哪个item,第二维j代表当前剩余容量,然后 value 当然就是遍历到i元素的时候,剩余容量为j的情况下能够达到的最大价值是多少

动态数组:

也就是压缩空间到两个数组,为什么能这么做呢?

因为每次 transit 的时候都会发现,只和上个 step 的值有关,因为状态转移方程为:

dp[i][j] = max(dp[i - 1][j], dp[i - 1][j - currentWeight] + currentValue)

这个状态转移方程的意思是说在每一步我可以决定把这个元素放到背包里,也可以不放到背包里~

放背包里当然就要减重喽,但会加价值;不放背包就当然不用减重喽,但价值也直接转移过来

一维数组:

还是挺好想到的8,直接 += 就行了~

416. Partition Equal Subset Sum

可以看成往一个容量为 sum / 2 的背包里放物品,那么每个数字就是物品了,如果放了1个或几个之后发现现在总价值已经是 sum / 2了,那就说明达到了符合题意的解,return true 就行了

那么怎么来定义我的dp数组呢?

我们要找几个和为 sum / 2 的数字,我会直接用一维的解决方法,然后 i 是当前背包的容量,也就是当前背包还能不能容下这个数字,如果当前背包能容下这个数字,我就会考虑 dp[i], dp[i - number] 这两项,他们只要有一个是 true 就说明我这个数字可以作为 subset 中的一员,这个 subset is being built toward (sum / 2),因此最终如果发现有能达到 sum / 2 的组合,就 return true