poj1787_完全背包(个数不是无限个)
题目链接:http://poj.org/problem?id=1787
题目大意:有1, 5, 10, 25面值的硬币, 求要用最多的硬币个数组成面值p?
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <algorithm> 5 #include <cstdlib> 6 #include <cmath> 7 #include <set> 8 #include <map> 9 #include <vector> 10 using namespace std; 11 12 int max(int a, int b) 13 { 14 return a > b ? a : b; 15 } 16 int dp[10010], num[5][10010], used[10010]; 17 int main() 18 { 19 int a[5], p, c[5], i, j; 20 a[1] = 1, a[2] = 5, a[3] = 10, a[4] = 25; 21 while(~scanf("%d %d %d %d %d", &p, &c[1], &c[2], &c[3], &c[4])) 22 { 23 if(p + c[1] + c[2] + c[3] + c[4] == 0) 24 break; 25 memset(dp, -1, sizeof(dp)); 26 memset(num, 0, sizeof(num)); 27 dp[0] = 0; 28 for(i = 1; i <= 4; i++) 29 { 30 memset(used, 0, sizeof(used)); 31 for(j = a[i]; j <= p; j++) 32 { 33 if(dp[j - a[i]] != -1 && used[j - a[i]] + 1 <= c[i] && dp[j] < dp[j - a[i]] + 1) 34 { 35 dp[j] = dp[j - a[i]] + 1; //组成p用的硬币总数 36 used[j] = used[j - a[i]] + 1;//组成P用的a[i]面值硬币的个数 37 num[i][j] = used[j]; 38 } 39 } 40 } 41 // cout << used[p] ; 42 if(dp[p] == -1) 43 printf("Charlie cannot buy coffee.\n"); 44 else 45 { 46 int t4 = used[p]; 47 int t3 = num[3][p - t4 * 25]; 48 int t2 = num[2][p - t4 * 25 - t3 * 10]; 49 int t1 = num[1][p - t4 * 25 - t3 * 10 - t2 * 5]; 50 printf("Throw in %d cents, %d nickels, %d dimes, and %d quarters.\n", t1, t2, t3, t4); 51 } 52 } 53 return 0; 54 }