hdu3033 分组背包(每组最少选一个)
题意:
Iserlohn 要买运动鞋,商店总共有N双运动鞋,他总共有M元钱,这些运动鞋分为K类,每类都有自己的编号i,每类中的每双鞋有单价m,和Iserlohn对这双鞋的评价价值v。Iserlohn想每一类运动鞋至少买一双,在不超过他所拥有的总金额前提下,使他得到的v最大。
http://acm.hdu.edu.cn/showproblem.php?pid=3033
1 #include <iostream> 2 #include <cstdio> 3 #include <vector> 4 #include <cstring> 5 using namespace std; 6 const int Ni = 12; 7 struct node{ 8 int m,val; 9 }; 10 int dp[Ni][10010]; 11 int main() 12 { 13 int n,tval,kind,i,j,k; 14 while(~scanf("%d%d%d",&n,&tval,&kind)) 15 { 16 vector<node> sneak[Ni]; 17 for(i=1;i<=n;i++) 18 { 19 node s; 20 scanf("%d%d%d",&j,&s.m,&s.val); 21 sneak[j].push_back(s); 22 } 23 bool flg=0; 24 for(i=1;i<=kind;i++) 25 { 26 if(sneak[i].size()==0) 27 { 28 flg=1; 29 printf("Impossible\n"); 30 break; 31 } 32 } 33 if(flg) continue; 34 memset(dp,-1,sizeof(dp)); 35 for(i=0;i<=tval;i++) dp[0][i]=0; 36 for(i=1;i<=kind;i++) 37 { 38 for(j=0;j<sneak[i].size();j++) 39 { 40 for(k=tval;k>=sneak[i][j].m;k--) 41 { 42 if(dp[i][k-sneak[i][j].m]!=-1) 43 dp[i][k]=max(dp[i][k],dp[i][k-sneak[i][j].m]+sneak[i][j].val); 44 //位置不能换,如第二组数据 45 if(dp[i-1][k-sneak[i][j].m]!=-1) 46 dp[i][k]=max(dp[i][k],dp[i-1][k-sneak[i][j].m]+sneak[i][j].val); 47 } 48 } 49 } 50 if(dp[kind][tval]==-1) printf("Impossible\n"); 51 else printf("%d\n",dp[kind][tval]); 52 } 53 return 0; 54 } 55 /* 56 3 5 3 57 1 2 5 58 2 2 1 59 3 2 2 60 61 3 5 3 62 1 0 5 63 2 0 1 64 3 0 2 65 66 3 5 3 67 1 0 0 68 2 0 0 69 3 0 0 70 */