模板请看上一篇博客
Whuacmers use coins.They have coins of value A1,A2,A3...An Silverland dollar. One day Hibix opened purse and found there were some coins. He decided to buy a very nice watch in a nearby shop. He wanted to pay the exact price(without change) and he known the price would not more than m.But he didn't know the exact price of the watch.
You are to write a program which reads n,m,A1,A2,A3...An and C1,C2,C3...Cn corresponding to the number of Tony's coins of value A1,A2,A3...An then calculate how many prices(form 1 to m) Tony can pay use these coins.
Input
The input contains several test cases. The first line of each test case contains two integers n(1 ≤ n ≤ 100),m(m ≤ 100000).The second line contains 2n integers, denoting A1,A2,A3...An,C1,C2,C3...Cn (1 ≤ Ai ≤ 100000,1 ≤ Ci ≤ 1000). The last test case is followed by two zeros.
Output
For each test case output the answer on a single line.
Sample Input
3 10
1 2 4 2 1 1
2 5
1 4 2 1
0 0
Sample Output
8
4
下面为百度翻译
巫师使用硬币,他们有价值的硬币A1、A2、A3……银币。有一天,希比克斯打开钱包,发现里面有一些硬币。他决定在附近的一家商店买一块好看的手表。他想支付准确的价格(没有变化),他知道价格不会超过M,但他不知道手表的确切价格。
你要写一个程序,读取N、M、A1、A2、A3……和托尼、C2、C3…CN对应的值A1、A2、A3的硬币的数目,然后计算托尼可以用多少钱(形式1到M)来使用这些硬币。
输入
输入包含多个测试用例。每个测试用例的第一行包含两个整数n(1±n=100),m(m=100000)。第二行包含2n个整数,表示a1、a2、a3…a、c1、c2、c3…cn(1个ω小于100000,1个小于i的CI为1000)。最后一个测试用例后面是两个零。
输出
对于每一个测试用例,在一行上输出答案。
说实话 还是没看懂 看题意吧
有n种货币和手表价格为m,单位货币的价值有val[i],单位货币的数量有vol[i],。求解带哪些 货币val*货币数量vol 可将手表买回且身上的钱总价值最大题解:注意时间上的优化,为避免超时,将多重背包问题分成完全背包和01背包问题,01背包再用二进制优化
题目的意思:
第一行输入,n,m分别表示n种硬币,m表示总钱数。
第二行输入n个硬币的价值,和n个硬币的数量。
输出这些硬币能表示的所有在m之内的硬币种数。
#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <cstring>
#define MAX 1000000
using namespace std;
int dp[MAX];//存储最后背包最大能存多少
int value[MAX],weight[MAX],number[MAX];//分别存的是物品的价值,每一个的重量以及数量
int bag;
void ZeroOnePack(int weight,int value )//01背包
{
int i;
for(i = bag; i>=weight; i--)
{
dp[i] = max(dp[i],dp[i-weight]+value);
}
}
void CompletePack(int weight,int value)//完全背包
{
int i;
for(i = weight; i<=bag; i++)
{
dp[i] = max(dp[i],dp[i-weight]+value);
}
}
void MultiplePack(int weight,int value,int number)//多重背包
{
if(bag<=number*weight)//如果总容量比这个物品的容量要小,那么这个物品可以直到取完,相当于完全背包
{
CompletePack(weight,value);
}
else//否则就将多重背包转化为01背包
{
int k = 1;
while(k<=number)
{
ZeroOnePack(k*weight,k*value);
number = number-k;
k = 2*k;//这里采用二进制思想
}
ZeroOnePack(number*weight,number*value);
}
}
int main()
{
int n;
while(~scanf("%d%d",&n,&bag))
{
if(n==0&&bag==0)
break;
int i,sum=0;
for(i = 0; i<n; i++)
scanf("%d",&value[i]);//输入价值
for(i=0;i<n;i++)
scanf("%d",&number[i]);//输入数量 此题没有物品的重量,可以理解为体积和价值相等
memset(dp,0,sizeof(dp));
for(i = 0; i<n; i++)
{
MultiplePack(value[i],value[i],number[i]);//调用多重背包,注意穿参的时候分别是重量,价值和数量
}
int ans=0;
for(i=1;i<=bag;i++)
{
if(i==dp[i])
ans++;
}
printf("%d
",ans);
}
return 0;
}
第一组样例dp 存的是1 2 3 4 5 6 7 8 8 8 i==dp[i]的意思是容量为i的最优解 dp[9]最大是8 不能组成9的硬币 所以不成立