Description

Farmer John has gone to town to buy some farm supplies. Being a very efficient man, he always pays for his goods in such a way that the smallest number of coins changes hands, i.e., the number of coins he uses to pay plus the number of coins he receives in change is minimized. Help him to determine what this minimum number is.

FJ wants to buy T (1 ≤ T ≤ 10,000) cents of supplies. The currency system has N (1 ≤ N ≤ 100) different coins, with values V1V2, ..., VN (1 ≤ Vi ≤ 120). Farmer John is carrying C1 coins of value V1C2 coins of value V2, ...., and CN coins of value VN (0 ≤ Ci ≤ 10,000). The shopkeeper has an unlimited supply of all the coins, and always makes change in the most efficient manner (although Farmer John must be sure to pay in a way that makes it possible to make the correct change).

Input

Line 1: Two space-separated integers: N and T
Line 2: N space-separated integers, respectively V1V2, ..., VN coins (V1, ...VN
Line 3: N space-separated integers, respectively C1C2, ..., CN

Output

Line 1: A line containing a single integer, the minimum number of coins involved in a payment and change-making. If it is impossible for Farmer John to pay and receive exact change, output -1.

Sample Input

3 70
5 25 50
5 2 1

Sample Output

3

Hint

Farmer John pays 75 cents using a 50 cents and a 25 cents coin, and receives a 5 cents coin in change, for a total of 3 coins used in the transaction.
 
题意:John去买东西,东西的价格是T(1 <= T <= 10000),John所在的地方有n(1 <= n <= 100)种的硬币,面值分别为V1, V2, ..., Vn (1 <= Vi <= 120)。John带了C1枚面值为V1的硬币,C2枚面值为V2的硬币,...,Cn枚面值为Vn的硬币(0 <= Ci <= 10000)。售货员那里每种硬币都有无限多个。问为了支付这个T,John给售货员的硬币数目加上售货员找回的零钱的硬币数目最少是多少。如果无法支付 T,输出-1 。

解法:支付时硬币数量有限制,为多重背包问题,通过二进制方法转化为01背包求解。找零时,硬币数量无限制,为完全背包问题。对两问题分别求解,然后找出差额为T时,两者和的最小值即为所示。

 
 
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std; #define met(a,b) (memset(a,b,sizeof(a)))
#define N 20000
#define INF 0x3f3f3f3f int V[], C[];
int v[N], c[N], dp[N];
int n, T, sum, k, Update; ///Update为更新的范围, 价值T最大为10000,而V[i]最大为120, 因此Update为10200便可以 void Init() ///将多重背包利用倍增法,转化为01背包
{ ///并解决一些初始化的问题
int i, j; k=;
for(i=; i<=n; i++)
{
for(j=; j<=C[i]; j*=)
{
v[k] = V[i]*j;
c[k++] = j;
C[i] -= j;
}
if(C[i])
{
v[k] = V[i]*C[i];
c[k++] = C[i];
C[i] = ;
}
}
k--; for(i=; i<=Update; i++)
dp[i] = INF;
} void First()
{
int i, j; dp[] = ;
for(i=; i<=k; i++)
{
for(j=Update; j>=v[i]; j--)
dp[j] = min(dp[j], dp[j-v[i]]+c[i]);
}
} int Secound()
{
int i, j; for(i=; i<=n; i++)
{
for(j=Update-V[i]; j>=; j--)
{///看好哦, 这里是加号,也就是从后面更新过来的, 于是第二重循环要逆着来
dp[j] = min(dp[j], dp[j+V[i]]+);
}
} return dp[T];
} int main()
{
while(scanf("%d%d", &n, &T)!=EOF)
{
int i;
sum=;
for(i=; i<=n; i++)
scanf("%d", &V[i]);
for(i=; i<=n; i++)
{
scanf("%d", &C[i]);
sum += V[i]*C[i];
}
Update=; Init(); ///初始化
First();///01背包
int ans = Secound(); ///完全背包 if(T>sum) printf("-1\n");
else
{
if(ans==INF) ///如果ans==INF说明并没有更新到dp[T],不能兑换到
printf("-1\n");
else
printf("%d\n", dp[T]);
} }
return ;
}

(混合背包 多重背包+完全背包)The Fewest Coins (poj 3260)的更多相关文章

  1. The Fewest Coins POJ - 3260

    The Fewest Coins POJ - 3260 完全背包+多重背包.基本思路是先通过背包分开求出"付出"指定数量钱和"找"指定数量钱时用的硬币数量最小值 ...

  2. POJ 3260 The Fewest Coins(完全背包+多重背包=混合背包)

    题目代号:POJ 3260 题目链接:http://poj.org/problem?id=3260 The Fewest Coins Time Limit: 2000MS Memory Limit: ...

  3. POJ3260——The Fewest Coins(多重背包+完全背包)

    The Fewest Coins DescriptionFarmer John has gone to town to buy some farm supplies. Being a very eff ...

  4. POJ 3260 The Fewest Coins(多重背包+全然背包)

    POJ 3260 The Fewest Coins(多重背包+全然背包) http://poj.org/problem?id=3260 题意: John要去买价值为m的商品. 如今的货币系统有n种货币 ...

  5. POJ3260The Fewest Coins[背包]

    The Fewest Coins Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 6299   Accepted: 1922 ...

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

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

  7. hdoj2191 珍惜现在,感恩生活(01背包 || 多重背包)

    题目链接 http://acm.hdu.edu.cn/showproblem.php?pid=2191 思路 由于每种大米可能不止一袋,所以是多重背包问题,可以直接使用解决多重背包问题的方法,也可以将 ...

  8. dp--01背包,完全背包,多重背包

    背包问题 以下代码 n是物品个数,m是背包容积 物品价值和重量int v[maxn],w[maxn]; 01背包 模板 for(int i = 0; i < n; i++) { for(int ...

  9. 多重背包转化成完全背包 E - Charlie's Change

    http://poj.org/problem?id=1787 这个题目我一看就觉得是一个多重背包,但是呢,我不知道怎么输出路径,所以无可奈何,我就只能看一下题解了. 看了题解发现居然是把多重背包转化成 ...

  10. nyoj 311-完全背包 (动态规划, 完全背包)

    311-完全背包 内存限制:64MB 时间限制:4000ms Special Judge: No accepted:5 submit:7 题目描述: 直接说题意,完全背包定义有N种物品和一个容量为V的 ...

随机推荐

  1. SQL语句中=null和is null

    平时经常会遇到这两种写法:IS NOT NULL与!=NULL.也经常会遇到数据库有符合条件!=NULL的数据,但是返回为空集合.实际上,是由于对二者使用区别理解不透彻. 默认情况下,推荐使用 IS ...

  2. 关于SharpZipLib压缩分散的文件及整理文件夹的方法

    今天为了解决压缩分散的文件时,发现想通过压缩对象直接进行文件夹整理很麻烦,因为SharpZipLib没有提供压缩进某个指定文件夹的功能,在反复分析了SharpZipLib提供的各个接口方法后,终于找到 ...

  3. Quickly place a window to another screen using only the keyboard

    http://askubuntu.com/questions/22207/quickly-place-a-window-to-another-screen-using-only-the-keyboar ...

  4. (转载)自动化基础普及之selenium是啥?

    转载:http://www.cnblogs.com/fnng/p/3980093.html Selenium 并不像QTP那样让人一下子就明白是什么?它是编程人员的最爱,但它却对测试新手产生了很大的阻 ...

  5. 解决程序出现“terminate called after throwing an instance of 'std::bad_alloc' what(): std::bad_alloc Aborted (core dumped)”的问题

    最近跑程序时出现了这么一个问题: terminate called after throwing an instance of 'std::bad_alloc' what(): std::bad_al ...

  6. C# 遍历文件夹下所有子文件夹中的文件,得到文件名

    假设a文件夹在F盘下,代码如下.将文件名输出到一个ListBox中using System.Data;using System.Drawing;using System.Linq;using Syst ...

  7. js中常用的操作

    1.js中常用的数组操作 2.js中常用的字符串操作 3.js中常用的时间日期操作 4.定时器

  8. HTTP、TCP、UDP以及SOCKET之间的区别/联系

    一.TCP/IP代表传输控制协议/网际协议,指的是一系列协组. 可分为四个层次:数据链路层.网络层.传输层和应用层. 在网络层:有IP协议.ICMP协议.ARP协议.RARP协议和BOOTP协议. 在 ...

  9. 错误:E:Unable to locate package ...

    安装NFS软件包: sudo apt-get install nfs-common 安装tftp软件: sudo apt-get install tftpd-hpa tftp-hpa 均出现此错误:E ...

  10. 第九章 springboot + mybatis + 多数据源 (AOP实现)(转载)

    本编博客转发自:http://www.cnblogs.com/java-zhao/p/5415896.html 1.ShopDao package com.xxx.firstboot.dao; imp ...