hdu 2955 Robberies

很久没写过题了。DP又是最拙计之处。只好从最简单的DP重新写一遍了

 

Problem Description

The aspiring Roy the Robber has seen a lot of American movies, and knowsthat the bad guys usually gets caught in the end, often because they become toogreedy. He has decided to work in the lucrative business of bank robbery onlyfor 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 andthe amount of cash they hold. He wants to make a calculated risk, and grab asmuch 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 aprobability less than this.

 

Input

The first line of input givesT, the number of cases. For each scenario, the first line of input gives afloating point number P, the probability Roy needs to be below, and an integerN, the number of banks he has plans for. Then follow N lines, where line jgives an integer Mj and a floating point number Pj .
Bank j contains Mj millions, and the probability of getting caught from robbingit is Pj .

 

Output

For each test case, output aline with the maximum number of millions he can expect to get while theprobability 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 probabilitiesare 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

 

 

题目大意就是告诉能承担概率为p及p以下的被抓概率,有n个银行。现在让求不被抓最多能抢多少。告诉每个银行的钱和被抓概率。

要不被抓,即是抢的所有的地方都不被抓,即抢的银行所有的不被抓概率之积。node保存银行信息。node[i].n为银行的钱,node[i].p为被抓概率。那么即是求(1-node[i].p)的积≤p且抢的钱最多为多少。dp[i]为抢了i时不被抓的概率。当dp[i]的值≤p时,i的最大值即为答案。

转移方程为:dp[j] = max(dp[j],dp[j-node[i].n]*(1-node[i].p))

#include<cstdio>
#include<cstring>
#include<cstdlib>
using namespace std;

typedef struct Node
{
	double p;
	int n;
};

Node node[110];
double dp[10010];//dp[i]表示能拿i时不被抓的概率

int main()
{
	int test ,n ,sum;
	double p;
	scanf("%d",&test);
	while(test--)
	{
		scanf("%lf%d",&p,&n);
		memset(dp,0,sizeof(dp));
		sum = 0;
		for(int i = 0;i<n;i++)
		{
			scanf("%d%lf",&node[i].n,&node[i].p);
			node[i].p = 1 - node[i].p;
			sum += node[i].n;
		}
		dp[0] = 1;
		for(int i = 0;i < n;i++)
		{
			for(int j = sum;j >=node[i].n;j--)
			{
				if(dp[j - node[i].n]!=0 && dp[j] < dp[j - node[i].n] * node[i].p)
				{
					dp[j] = dp[j - node[i].n] * node[i].p;
				}
			}
		}
		for(int i = sum;i>=0;i--)
		{
			if(dp[i]>=1-p)
			{
				printf("%d\n",i);
				break;
			}
		}
	}
	return 0;
}


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值