Description
Input
Output
Sample Input
3 7 40 3 5 23 8 2 52 6
Sample Output
48
这题先要对a_i进行升序排序,因为每一个长度都有最大的限度,所以从最大限度值最小的开始背包。然后注意初始值都设为-1,dp[0]=0,因为这里要求的是恰好到一个高度,并不是小于等于就行(有点抽象,仔细体会一下)。
#include<stdio.h> #include<string.h> #include<algorithm> using namespace std; int max(int a,int b){ return a>b?a:b; } struct node{ int h,a,num; }b[500]; bool cmp(node c,node d){ return c.a<d.a; } int dp[40050]; int main() { int n,m,i,j,k,sum; while(scanf("%d",&n)!=EOF) { m=0; for(i=1;i<=n;i++){ scanf("%d%d%d",&b[i].h,&b[i].a,&b[i].num); if(b[i].a>m)m=b[i].a; } sort(b+1,b+1+n,cmp); memset(dp,-1,sizeof(dp)); dp[0]=0; for(i=1;i<=n;i++){ if(b[i].h*b[i].num>=b[i].a){ for(j=b[i].h;j<=b[i].a;j++){ if(dp[j-b[i].h]!=-1)dp[j]=0; } } else{ k=1;sum=0; while(sum+k<b[i].num){ sum+=k; for(j=b[i].a;j>=k*b[i].h;j--){ if(dp[j-k*b[i].h]!=-1)dp[j]=0; } k*=2; } k=b[i].num-sum; for(j=b[i].a;j>=k*b[i].h;j--){ if(dp[j-k*b[i].h]!=-1)dp[j]=0; } } } for(i=m;i>=0;i--){ if(dp[i]!=-1){ printf("%d\n",i);break; } } } return 0; }