题目链接:http://cojs.tk/cogs/problem/problem.php?pid=992
分析:
多重背包。
首先可以全部拆开当做01背包处理,但是这样会超时。
收到背包九讲的启发,可以用倍增的思想。
用1,2,4等数表示出所有的数,这样可以大大减小需要处理的个数。
代码:
#include<cstdio>
#include<iostream>
using namespace std;
int w,n,v,c,f[50000],co;
int main()
{
freopen("treasure.in","r",stdin);
freopen("treasure.out","w",stdout);
scanf("%d%d",&n,&w);
for (int i=1;i<=n;++i)
{
int k=1;
scanf("%d %d %d",&v,&c,&co);
while (co-k>=0)
{
co-=k;
for (int j=w;j>=c*k;--j)
f[j]=max(f[j],f[j-c*k]+k*v);
k<<=1;
}
k=co;
if (k<=0) continue;
for (int j=w;j>=k*c;--j)
f[j]=max(f[j],f[j-c*k]+v*k);
}
cout<<f[w];
return 0;
}