Time limit

1000 ms
Memory limit 30000 kB

description

Charlie is a driver of Advanced Cargo Movement, Ltd. Charlie drives a lot and so he often buys coffee at coffee vending machines at motorests. Charlie hates change. That is basically the setup of your next task.

Your program will be given numbers and types of coins Charlie has and the coffee price. The coffee vending machines accept coins of values 1, 5, 10, and 25 cents. The program should output which coins Charlie has to use paying the coffee so that he uses as many coins as possible. Because Charlie really does not want any change back he wants to pay the price exactly.

input

Each line of the input contains five integer numbers separated by a single space describing one situation to solve. The first integer on the line P, 1 <= P <= 10 000, is the coffee price in cents. Next four integers, C1, C2, C3, C4, 0 <= Ci <= 10 000, are the numbers of cents, nickels (5 cents), dimes (10 cents), and quarters (25 cents) in Charlie's valet. The last line of the input contains five zeros and no output should be generated for it.

For each situation, your program should output one line containing the string "Throw in T1 cents, T2 nickels, T3 dimes, and T4 quarters.", where T1, T2, T3, T4 are the numbers of coins of appropriate values Charlie should use to pay the coffee while using as many coins as possible. In the case Charlie does not possess enough change to pay the price of the coffee exactly, your program should output "Charlie cannot buy coffee.".

sample input

12 5 3 1 2

16 0 0 0 1

0 0 0 0 0

sample output

Throw in 2 cents, 2 nickels, 0 dimes, and 0 quarters.

Charlie cannot buy coffee.

题目解读

代码思路是看别的代码得到的,对其代码进行了优化并加了自己的注释,其中利用了映射来加强练习。

总体来说,就是个多重背包加上路径记忆。

代码区

#include<cstdio>
#include<algorithm>
#include<cstring>
#include<iostream>
#include<map>
using namespace std; const int M = 10003; const int INF = 0x3f3f3f3f; map<int, int>num, val; int dp[M], used[M], path[M]; //dp[i]表示凑齐价值 i 时所用的最大硬币数量
//used[i]表示在价值 i 时已经用了当前种类硬币数量
//path[i] 下标表示当前价值, 值表示凑成价值 i 之前的总价值,即用了
//某一硬币之前的价值, i - path[i] 则表示这一过程中使用的硬币价值 int main()
{
int p ,c1 ,c2,c3,c4;
while(cin>>p>>c1>>c2>>c3>>c4)
{
if (p + c1 + c2 + c3 + c4 == 0)break; num[1] = c1;
num[2] = c2;
num[3] = c3;
num[4] = c4; val[1] = 1;
val[2] = 5;
val[3] = 10;
val[4] = 25; //练习一下映射 memset(path, 0, sizeof(path)); //路径初始化 for(int i = 1 ;i <= p ; i ++)
{
dp[i] = -INF;
}
dp[0] = 0; //基础部分,将除了起点设置为0外,其余的初始值均为负无穷大,
//意味着某一状态只有从起点开始转移,其值才有效
for (int i = 1; i <= 4; i++)
{
memset(used, 0, sizeof(used)); //初始化各个价值的硬币使用数
for(int j = val[i] ; j<= p ; j++)
{
if (used[j - val[i]] < num[i] && dp[j-val[i]] >=0 && dp[j - val[i]] + 1 > dp[j])
//硬币数量足够转移,且转移后的硬币数量更多,以及转移的前一个状态有效
{
dp[j] = dp[j - val[i]] + 1; //表示从前一个状态转移过来
used[j] = used[j - val[i]] + 1; //表示从 j - val[i] 价值转移而来用了一个硬币
path[j] = j - val[i]; //下标表示当前价值,其值表示转移起点的价值 }
}
}
if(dp[p] < 0) //若dp[i]<0表示这一价值无法凑齐
{
cout << "Charlie cannot buy coffee." << endl;
continue;
}
map<int, int>ans;
ans[1] = 0;
ans[5] = 0;
ans[10] = 0;
ans[25] = 0; //代表各个价值对应的硬币的使用数量 int now = p; //从终点开始回溯
while(true)
{
if (now == 0)break; //价值为0 ,代表已经走回了起点
ans[now - path[now]]++; //now - path[now] 表示两个状态之间的差值,此差值就是各个硬币的价值,所以对应价值的硬币数量加一
now = path[now]; //为下一次做准备
}
printf("Throw in %d cents, %d nickels, %d dimes, and %d quarters.\n", ans[1], ans[5], ans[10], ans[25]); }
return 0;
}

Charlie's Change POJ - 1787的更多相关文章

  1. (多重背包+记录路径)Charlie's Change (poj 1787)

    http://poj.org/problem?id=1787   描述 Charlie is a driver of Advanced Cargo Movement, Ltd. Charlie dri ...

  2. poj 1787 Charlie's Change (多重背包可作完全背包)

    Charlie's Change Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 3792   Accepted: 1144 ...

  3. poj 1787 背包+记录路径

    http://poj.org/problem?id=1787 Charlie's Change Time Limit: 1000MS   Memory Limit: 30000K Total Subm ...

  4. 专题复习--背包问题+例题(HDU 2602 、POJ 2063、 POJ 1787、 UVA 674 、UVA 147)

    *注 虽然没什么人看我的博客但我还是要认认真真写给自己看 背包问题应用场景给定 n 种物品和一个背包.物品 i 的重量是 w i ,其价值为 v i ,背包的容量为C.应该如何选择装入背包中的物品,使 ...

  5. Charlie's Change(完全背包+路径记忆)

    Charlie's Change Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 3176   Accepted: 913 D ...

  6. Charlie's Change(完全背包记录路径)

    Charlie is a driver of Advanced Cargo Movement, Ltd. Charlie drives a lot and so he often buys coffe ...

  7. B - Charlie's Change

    Charlie is a driver of Advanced Cargo Movement, Ltd. Charlie drives a lot and so he often buys coffe ...

  8. poj1787 Charlie's Change

    Description Charlie is a driver of Advanced Cargo Movement, Ltd. Charlie drives a lot and so he ofte ...

  9. [POJ 1787]Charlie's Change (动态规划)

    题目链接:http://poj.org/problem?id=1787 题意:有4种货币分别是1元,5元,10元,20元.现在告诉你这四种货币分别有多少个,问你正好凑出P元钱最多可以用多少货币.每种货 ...

随机推荐

  1. 推荐系统系列(二):FFM理论与实践

    背景 在CTR/CVR预估任务中,除了FM模型[2] 之外,后起之秀FFM(Field-aware Factorization Machine)模型同样表现亮眼.FFM可以看作是FM的升级版,Yuch ...

  2. MessageListenerAdapter--消息监听适配器

    我们把之前的消息监听代码注释,可以不用直接加消息监听,而是采用MessageListenerAdapter的方式,我们来学习下如何使用默认的handleMessage,自定义方法名,自定义转换器. 适 ...

  3. JavaWeb-SpringSecurity自定义登陆配置

    系列博文 项目已上传至guthub 传送门 JavaWeb-SpringSecurity初认识 传送门 JavaWeb-SpringSecurity在数据库中查询登陆用户 传送门 JavaWeb-Sp ...

  4. Partial Dependence Plot

    Partial Dependence就是用来解释某个特征和目标值y的关系的,一般是通过画出Partial Dependence Plot(PDP)来体现. PDP是依赖于模型本身的,所以我们需要先训练 ...

  5. flask读书记录

    1. 在flask中,如果我们在视图函数中使用data = request.get_json()方法获取数据,那么在客户端发送POST请求时,就需要设置设置正确的Content-Type首部.在aja ...

  6. 使用 VS2015 编译并调试 ffmpeg

    导读 ffmpeg 是音频处理方面非常强大非常有名的开源项目了,然而如 雷神 所说,“FFMPEG 难度比较大,却没有一个循序渐进,由简单到复杂的教程.现在网上的有关FFMPEG的教程多半难度比较大, ...

  7. 【好书推荐】9、安卓Andorid编程吐血整理100+本

    点开即可

  8. python函数(一)

    今天记一下学到的python函数相关知识. 目录: 1.函数简介 2.函数定义 3.函数参数 第一部分:函数简介    我们在编程过程中往往会碰到这样的事情-----很多地方都用到了相同的一段代码.虽 ...

  9. ubuntu最近升级到最新的linux内核后,网络无法使用怎么办?

    答:进入旧的内核中编译需要的网卡模块 1. 启动旧的内核进入系统 2. 安装新内核源码 3. 找出当前的网卡型号 4. 尝试卸载某个与网卡相关的内核模块,观察是否影响当前网卡的使用,如果有影响,那么便 ...

  10. vs2010 SetUp 安装软件时,界面出现乱码的问题

    AppLocale在简体中文系统里使用之后, 会令某些简体中文的MSI形式的安装程序 显示乱码(比如: OFFICE2000简体中文版安装程序). 解决方法: 方法一: 卸载AppLocale即可解决 ...