zoukankan      html  css  js  c++  java
  • hdoj2955 Robberies(01背包)

    题目链接

    http://acm.hdu.edu.cn/showproblem.php?pid=2955

    题意

    有n家银行,每家银行有两个属性:钱数m,概率p,p表示抢这家银行被逮着的概率。有一个人想抢银行,他认为只要在他抢一些银行后,被逮着的概率(指抢完所有银行被逮着的概率)小于pm就可以抢,求这个人最多可以抢多少钱。

    思路

    01背包问题,这题要注意钱数是背包容量,成功逃走的概率为价值(如果反过来会发现代码没办法写,因为反过来数组dp下标为小数)。数组dp[i]表示在抢的钱数为i的情况下,成功逃走概率的最大值。求出成功逃走概率的最大值后,1-最大值即为被逮着概率的最小值,再拿最小值与pm比较即可。此外还要注意dp数组的初始化。

    代码

     1 #include <algorithm>
     2 #include <iostream>
     3 #include <cstring>
     4 #include <cstdio>
     5 using namespace std;
     6 
     7 const int N = 110;
     8 const int M = 100 * 100 + 10;
     9 double p[N];
    10 int m[N];
    11 double dp[M];
    12 
    13 int main()
    14 {
    15     //freopen("hdoj2955.txt", "r", stdin);
    16     int t, n;
    17     double pm;
    18     cin >> t;
    19     while (t--)
    20     {
    21         int sum = 0;
    22         cin >> pm >> n;
    23         for (int i = 0; i < n; i++)
    24         {
    25             cin >> m[i] >> p[i];
    26             p[i] = 1 - p[i];    //成功逃走的概率
    27             sum += m[i];
    28         }
    29 
    30         memset(dp, 0, sizeof(dp));
    31         dp[0] = 1;    //没有抢钱,成功逃走的概率为1
    32         for (int i = 0; i < n; i++)
    33         {
    34             for (int j = sum; j >= m[i]; j--)
    35                 dp[j] = max(dp[j], dp[j - m[i]] * p[i]);
    36         }
    37 
    38         for (int i = sum; i >= 0; i--)
    39             if (1 - dp[i] < pm)
    40             {
    41                 cout << i << endl;
    42                 break;
    43             }
    44     }
    45     return 0;
    46 }
  • 相关阅读:
    bs4的学习
    mysqldb模块的简单用法
    起点中文网(主要是在目录下创建文件)
    怎么把列表转化为字符串
    GUI开发者桌面搜索文件工具
    用表格形式保存文档 xlwt
    如何解决编码有问题
    影魔
    龙与地下城
    不等关系
  • 原文地址:https://www.cnblogs.com/sench/p/8017431.html
Copyright © 2011-2022 走看看