如何把背包问题转化成动态规划
绪言
每当有人看到这样的题目:
有n 种物品(各有一件/都有无限件/有有限件),它们有各自的重量和价值,现有给定容量的背包,如何让背包里装入的物品具有最大的价值总和?
那个人可能会喊道:
我的妈呀。。。又是背包【哭】
今天我一定要搞懂背包!
这个人,是你,也(就)是我。(dalao们好!)
01背包
这是最基础的背包问题
我们不妨从输入讲起
input
可以用结构体struct
struct str{ int w; int v;} object[n];
也可以用数组
int v[n],w[n];
为表达方便,以下代码使用数组
solution
这里用一种我从未见过的表达方式:
用dp[i][j]表示以j为剩余容量,选择性的放入前i个物品的最大价值。
初始化:
dp[0][j]=dp[i][0]=0;
进入下一步的选择:
对于每一个物品,你有两个选择:
容量不足,装不下它:
此时的价值==前i-1个物品时的价值,即dp[i][j]=dp[i-1][j]
容量足以装下它,but不一定能达到当前最优价:
在选与不选中选择一个最优的,即dp[i][j]=max{dp[i-1][j],dp[i-1][j-w[i]]+v[i]};
其中dp[i-1][j]为不装情况,dp[i-1][j-w[i]]+v[i]为装的情况
这就是递推式了
dp[i][j]=max{dp[i-1][j],dp[i-1][j-w[i]]+v[i]};
Code