最大报销额
Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 17414 Accepted Submission(s): 5105
Problem Description
现有一笔经费可以报销一定额度的发票。允许报销的发票类型包括买图书(A类)、文具(B类)、差旅(C类),要求每张发票的总额不得超过1000元,每张发票上,单项物品的价值不得超过600元。现请你编写程序,在给出的一堆发票中找出可以报销的、不超过给定额度的最大报销额。
Input
测试输入包含若干测试用例。每个测试用例的第1行包含两个正数 Q 和 N,其中 Q 是给定的报销额度,N(<=30)是发票张数。随后是 N 行输入,每行的格式为:
m Type_1:price_1 Type_2:price_2 ... Type_m:price_m
其中正整数 m 是这张发票上所开物品的件数,Type_i 和 price_i 是第 i 项物品的种类和价值。物品种类用一个大写英文字母表示。当N为0时,全部输入结束,相应的结果不要输出。
m Type_1:price_1 Type_2:price_2 ... Type_m:price_m
其中正整数 m 是这张发票上所开物品的件数,Type_i 和 price_i 是第 i 项物品的种类和价值。物品种类用一个大写英文字母表示。当N为0时,全部输入结束,相应的结果不要输出。
Output
对每个测试用例输出1行,即可以报销的最大数额,精确到小数点后2位。
Sample Input
200.00 3 2 A:23.50 B:100.00 1 C:650.00 3 A:59.99 A:120.00 X:10.00 1200.00 2 2 B:600.00 A:400.00 1 C:200.50 1200.50 3 2 B:600.00 A:400.00 1 C:200.50 1 A:100.00 100.00 0
Sample Output
123.50 1000.00 1200.50
注意几点:1、同类物品会出现多次,其总和不能大于600;
2、每张发票要么报销要么不报销,且总价值不大于1000;
3、只能报销A、B、C三种消费类型。
然后,对于每个发票其耗费为1,价值为总钱数,用01背包求解。
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define N 35
double dp[N],a[N];
int main()
{
int i,j,n,q,flag,cnt;
double t,money;
char ch;
while(scanf("%lf%d",&money,&n),n)
{
for(i=cnt=0;i<n;i++)
{
scanf("%d",&q);
flag=1;
double s1=0,s2=0,s3=0;
//getchar();
while(q--)
{
getchar();
scanf("%c:%lf",&ch,&t);
if(ch=='A')
s1+=t;
else if(ch=='B')
s2+=t;
else if(ch=='C')
s3+=t;
else
flag=0;
if(s1>600||s2>600||s3>600)
flag=0;
if(s1+s2+s3>1000)
flag=0;
}
if(flag)
a[cnt++]=s1+s2+s3;
}
memset(dp,0,sizeof(dp));
for(i=0;i<cnt;i++)
{
for(j=cnt;j>=1;j--)
dp[j]=max(dp[j],dp[j-1]+a[i]);
}
double ans=0;
for(i=0;i<=cnt;i++)
if(dp[i]>ans&&dp[i]<=money)
ans=dp[i];
printf("%.2f\n",ans);
}
return 0;
}
Robberies
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 13660 Accepted Submission(s): 5027
Problem Description
The aspiring Roy the Robber has seen a lot of American movies, and knows that the bad guys usually gets caught in the end, often because they become too greedy. He has decided to work in the lucrative business of bank robbery only for a short while, before retiring to a comfortable job at a university.
For a few months now, Roy has been assessing the security of various banks and the amount of cash they hold. He wants to make a calculated risk, and grab as much money as possible.
His mother, Ola, has decided upon a tolerable probability of getting caught. She feels that he is safe enough if the banks he robs together give a probability less than this.
For a few months now, Roy has been assessing the security of various banks and the amount of cash they hold. He wants to make a calculated risk, and grab as much money as possible.
His mother, Ola, has decided upon a tolerable probability of getting caught. She feels that he is safe enough if the banks he robs together give a probability less than this.
Input
The first line of input gives T, the number of cases. For each scenario, the first line of input gives a floating point number P, the probability Roy needs to be below, and an integer N, the number of banks he has plans for. Then follow N lines, where line j gives an integer Mj and a floating point number Pj .
Bank j contains Mj millions, and the probability of getting caught from robbing it is Pj .
Bank j contains Mj millions, and the probability of getting caught from robbing it is Pj .
Output
For each test case, output a line with the maximum number of millions he can expect to get while the probability of getting caught is less than the limit set.
Notes and Constraints
0 < T <= 100
0.0 <= P <= 1.0
0 < N <= 100
0 < Mj <= 100
0.0 <= Pj <= 1.0
A bank goes bankrupt if it is robbed, and you may assume that all probabilities are independent as the police have very low funds.
Notes and Constraints
0 < T <= 100
0.0 <= P <= 1.0
0 < N <= 100
0 < Mj <= 100
0.0 <= Pj <= 1.0
A bank goes bankrupt if it is robbed, and you may assume that all probabilities are independent as the police have very low funds.
Sample Input
3 0.04 3 1 0.02 2 0.03 3 0.05 0.06 3 2 0.03 2 0.03 3 0.05 0.10 3 1 0.03 2 0.02 3 0.05
Sample Output
2 4 6
要点:对于强盗来说,只有他抢劫第一家银行不被抓的情况下,他才能抢劫第二家银行。所以,可以求出抢劫每家银行不被抓的概率,然后,用01背包求能抢劫的最大钱数。
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
#define N 10005
double dp[N],p[105];
int a[105];
void inti(int all)
{
int i;
for(i=0;i<=all;i++)
dp[i]=0;
dp[0]=1;
}
int main()
{
int T,i,j,n,all;
double t,p0;
scanf("%d",&T);
while(T--)
{
scanf("%lf%d",&t,&n);
all=0;
p0=1-t; //安全的概率大于等于p0,不被抓
for(i=0;i<n;i++)
{
scanf("%d%lf",&a[i],&t);
p[i]=1-t; //不被抓概率
all+=a[i]; //求总钱数
}
inti(all); //初始化
for(i=0;i<n;i++) //求出每种钱数不被抓概率
{
for(j=all;j>=a[i];j--)
{
dp[j]=max(dp[j],dp[j-a[i]]*p[i]);
}
}
for(i=all;i>=0;i--) //在不被抓情况下求出最大价值
if(dp[i]>=p0)
break;
printf("%d\n",i);
}
return 0;
}