简单的多重背包,两层循环,用sum数组表示一下钱币数目还够不够用即可
#include <iostream> #include<stdio.h> #include<algorithm> #include<string.h> #include<fstream> using namespace std; int w[15]; int d[15]; int sum[100005]; int dp[100005]; int main(){ //freopen("aaa.txt","r",stdin); int n,m; while(~scanf("%d%d",&m,&n)){ memset(dp,0,sizeof(dp)); for(int i=1;i<=n;i++) scanf("%d%d",&d[i],&w[i]); int ans=0; dp[0]=1; for(int i=1;i<=n;i++){ memset(sum,0,sizeof(sum));//每次清空sum,sum[i]表示钱数为i时用掉了几个第i种钱币 for(int j=w[i];j<=m;j++){ if(!dp[j] && dp[j-w[i]] && sum[j-w[i]]<d[i])//如果j元未得到过并且j-w[i]元得到过并且现在的i中钱币还有,就能得到j了 { dp[j]=1; sum[j]=(sum[j-w[i]]+1); } } } int i; for(i=m;i>=0;i--)//从最大往前找,找到就退出啦 if(dp[i]!=0) break; printf("%d\n",i); } return 0; }