hdu 3449(有依赖的01背包)

http://acm.hdu.edu.cn/showproblem.php?pid=3449

题意:

有很多个箱子,想买箱子中的物品必须先买下箱子,典型的依赖背包

dp[i][j]代表前i个箱子花费j的钱能获得的最大价值

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 using namespace std;
 5 const int Ni = 55;
 6 const int Mi = 100005;
 7 int dp[Ni][Mi];
 8 int main()
 9 {
10     int n,m,tv,i,j,k,pi,c,w;
11     memset(dp[0],0,sizeof(dp[0]));
12     while(~scanf("%d%d",&n,&tv))
13     {
14         for(i=1;i<=n;i++)
15         {
16             scanf("%d%d",&pi,&m);
17             for(j=0;j<pi;j++) dp[i][j]=-1;
18             for(j=tv;j>=pi;j--) dp[i][j]=dp[i-1][j-pi];
19             for(k=0;k<m;k++)
20             {
21                 scanf("%d%d",&c,&w);
22                 for(j=tv;j>=c;j--) if(dp[i][j-c]!=-1)
23                  dp[i][j]=max(dp[i][j],dp[i][j-c]+w);
24             }
25             for(j=tv;j>=0;j--) dp[i][j]=max(dp[i][j],dp[i-1][j]);
26         }
27         printf("%d\n",dp[n][tv]);
28     }
29     return 0;
30 }

 

优化到一维:

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 using namespace std;
 5 const int Mi = 100005;
 6 int dp[Mi];
 7 int arr[Mi];
 8 inline int max(int a,int b) {return a>b? a:b;}
 9 int main()
10 {
11     int n,m,tv,i,j,k,pi,c,w;
12     while(~scanf("%d%d",&n,&tv))
13     {
14         memset(dp,0,sizeof(dp));
15         for(i=1;i<=n;i++)
16         {
17             scanf("%d%d",&pi,&m);
18             memcpy(arr,dp,sizeof(dp));//继承
19             for(k=0;k<m;k++)
20             {
21                 scanf("%d%d",&c,&w);
22                 for(j=tv-pi;j>=c;j--)//对附件进行01背包
23                 {
24                     arr[j]=max(arr[j],arr[j-c]+w);
25                 }
26             }
27             for(j=pi;j<=tv;j++)//更新
28                 dp[j]=max(dp[j],arr[j-pi]);
29         }
30         printf("%d\n",dp[tv]);
31     }
32     return 0;
33 }

 

posted @ 2012-08-17 20:53  qijinbiao1  阅读(1138)  评论(0编辑  收藏  举报