【HDU1203 HDU2955 01背包中的简单概率问题处理】

HDU1203
Speakless很早就想出国,现在他已经考完了所有需要的考试,准备了所有要准备的材料,于是,便需要去申请学校了。
要申请国外的任何大学,你都要交纳一定的申请费用,这可是很惊人的。Speakless没有多少钱,总共只攒了n万美元。
他将在m个学校中选择若干的(当然要在他的经济承受范围内)。每个学校都有不同的申请费用a(万美元),并且Speakless估计了他得到这个学校offer的可能性b。
不同学校之间是否得到offer不会互相影响。帮助他计算一下,他可以收到至少一份offer的最大概率。
(如果Speakless选择了多个学校,得到任意一个学校的offer都可以)。

求至少获得一个的offer的最大概率,那么反面就是一个都没有获得的最小概率

#include <bits/stdc++.h>
#include <iostream>
#define X 10005
#define inf 0x3f3f3f3f
#define PI 3.141592653589793238462643383
#define IO  ios::sync_with_stdio(false),cin.tie(0), cout.tie(0);
#pragma comment(linker, "/STACK:1024000000,1024000000")
using namespace std;
typedef long long ll;
const ll mod=1e9+7;
const int maxn=1e6+10;
double w[maxn];
double ww[maxn];
int c[maxn];
double dp[maxn];
double dp1[maxn];
int main()
{
    int n,m;
    while(cin>>m>>n,n!=0||m!=0)
    {
        for(int i=0;i<n;++i){cin>>c[i]>>w[i];w[i]=1-w[i];}
        for(int i=0;i<=m;++i)dp[i]=1.0;//memset(dp,1,sizeof(dp));
        dp[0]=1;dp1[0]=1;
        for(int i=0;i<n;++i)
        {
            for(int j=m;j>=c[i];--j)
                dp[j]=min(dp[j],dp[j-c[i]]*w[i]);
        }
        printf("%.1lf%%\n",(1-dp[m])*100.0);
    }
}

HDU2955
印象好题。。。。
给定一个被抓的概率p,还有一些银行,给定这些银行的钱数以及抢劫这些银行被抓的概率。
求在被抓的概率不大于p的情况下最多可以抢到多少钱。
自带bug把概率当作背包,钱数当作容量,这样没法确定精度是多少位,也没法计算概率
总结正确姿势:把被抓概率转化为可逃跑概率,总的金钱当作背包(也没有给出背包的总容量,把总的转化为背包容量),可逃跑的概率为价值
还有就是概率是满足乘法原理的
初始化问题:难道紧是使逃跑的概率尽量大,这一要求,才初始化为-1嘛????
 

#include <bits/stdc++.h>
#include <iostream>
#define X 10005
#define inf 0x3f3f3f3f
#define PI 3.141592653589793238462643383
#define IO  ios::sync_with_stdio(false),cin.tie(0), cout.tie(0);
#pragma comment(linker, "/STACK:1024000000,1024000000")
using namespace std;
typedef long long ll;
const ll moad=1e9+7;
const int maxn=1e6+10;
double dp[maxn];
int w[maxn];
int vis[maxn];
double c[maxn];
int main()
{
    int t;
    double p,n,_;
    cin>>t;
    while(t--)
    {
        int sum=0;
        cin>>p>>n;
        double __=1.0-p;
        for(int i=0;i<n;++i){cin>>w[i]>>_;c[i]=1.0-_;sum+=w[i];}
        //sum能抢到的最大量
        for(int i=1;i<maxn;++i)dp[i]=-1;
        dp[0]=1.0;
        for(int i=0;i<n;++i)
        {
            for(int j=sum;j>=w[i];--j)
                dp[j]=max(dp[j],dp[j-w[i]]*c[i]);
        }
        for(int i=sum;i>=0;--i)
           if(dp[i]>=__)
            {cout<<i<<endl;break;}
    }
    return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值