01背包问题。
传送门:http://acm.hdu.edu.cn/showproblem.php?pid=1864
#include <map>
#include <set>
#include <queue>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
using namespace std;
int total;
int dp[3000005]; // 背包最大为300,000;30个物品,每个价值1000元*100;
int N ;
void Deal_with() {
double temp;
int m;
int tempA,tempB,tempC;
char tempc;
int flag = 0;
while(scanf("%lf %d",&temp,&N),N) {
total = temp * 100;
memset(dp,0,sizeof(dp));
for(int i = 1 ; i <= N ; i++) {
scanf("%d",&m);
flag = 0; tempA = 0; tempB = 0; tempC = 0;
for(int j = 1 ; j <= m ; j++) {
scanf(" %c:%lf",&tempc,&temp);
if(tempc == 'A') tempA += temp * 100;
else if(tempc == 'B') tempB += temp * 100;
else if(tempc == 'C') tempC += temp * 100;
else {
flag = 1;
}
//printf("%c:%.2lf\n",tempc,temp);
}
int now = tempA + tempB + tempC;
if(now > 100000) flag = 1;
if(tempA > 60000 || tempB > 60000 || tempC > 60000) flag = 1;
if(flag) continue;
for(int j = total ; j >= now ; j--) {
dp[j] = max(dp[j],dp[j-now]+now);
}
}
printf("%.2lf\n",(double)dp[total]/100.0);
}
}
int main(void) {
freopen("a.in","r",stdin);
Deal_with();
return 0;
}
//将每个物品的价值*100后,进行DP;