一、01背包
有N件物品,一个容量为V的背包,第i件物品的重量为c[i],价值为v[i],求将哪些装入背包可使价值最大。
用dp[i][j]表示前i件物品恰放入一个容量为j的背包可以获得的最大价值。
当不放的时候则是:dp[i][j] = dp[i-1][j];
放的时候则是:dp[i][j] = dp[i-1][j-c[i]]+v[i];
如果不放,就保持上一种状态,如果放,就在牺牲容积的情况下增加价值。由于我们求的是最大价值,则其状态转移方程便是:dp[i][j]=max{ dp[i-1][j], dp[i-1][j-c[i]]+v[i] };
代码
#include<iostream>
#include<algorithm>
using namespace std;
int dp[21][1010];
int v[21],c[21];
int main()
{
int N,V;
cin>>N>>V;
for(int i=1;i<=N;i++)
cin>>v[i]>>c[i];
for(int i=1;i<=N;i++)
for(int j=V;j>=1;j--)//循环倒序
if(j>=c[i])
dp[i][j]=max(dp[i-1][j-c[i]]+v[i],dp[i-1][j]);
else
dp[i][j]=dp[i-1][j];
cout<<dp[N][V]<<endl;
return 0;
}
二、完全背包
有N种物品,一个容量为V的背包,每种物品都有无限件可用,第i种物品的费用为c[i],价值为v[i],求将哪些物品装入背包可试这些物品的费用总和不超过背包容量。且价值总和最大。
代码
for(int i=1;i<=n;i++)
for(int j=1;j<=V;j++)//循环正序
{
if(j>=c[i])
dp[i][j]=max(dp[i-1][j],dp[i-1][j-c[i]]+v[i]);
else
dp[i][j]=dp[i-1][j];
}