题目大意:一道混合背包模板。
解题思路:分三种情况讨论,01和完全没什么问题,多重背包需要把物品分成$log W[i]$件,然后01即可,分成W[i]件01会TLE。
读优大法好!
C++ Code:
#include<cstdio> #include<cctype> using namespace std; #define max(i,j)(((i)>(j))?(i):(j)) char buf[4000004]; int bufpos; inline void init(){ bufpos=0; buf[fread(buf,1,4000000,stdin)]=' '; } inline int readint(){ int p=0,flag=false; for(;!isdigit(buf[bufpos]);bufpos++)flag=(buf[bufpos]=='-'); for(;isdigit(buf[bufpos]);bufpos++) p=(p<<3)+(p<<1)+buf[bufpos]-'0'; return (flag)?(-p):(p); } int n,v,f[200002]; int main(){ init(); n=readint(),v=readint(); while(n--){ int V=readint(),W=readint(),M=readint(); if(M==1) for(int i=v;i>=V;--i) f[i]=max(f[i],f[i-V]+W); else if(M==-1) for(int i=V;i<=v;++i) f[i]=max(f[i],f[i-V]+W); else{ int k=1,p=1; while(p<=M){ for(int i=v;i>=V*k;--i) f[i]=max(f[i],f[i-V*k]+W*k); p+=(k*=2); } p=M-p+k; for(int i=v;i>=V*p;--i) f[i]=max(f[i],f[i-V*p]+W*p); } } printf("%d ",f[v]); return 0; }