其他分享
首页 > 其他分享> > [HDU4336]Card Collector

[HDU4336]Card Collector

作者:互联网

题目描述

题目传送门:http://acm.hdu.edu.cn/showproblem.php?pid=4336

题目大意:有\(n\)张卡牌,每秒有\(p_i\)的概率买到第\(i\)张卡,\(\sum p_i\leqslant 1\),问期望多少秒之后集齐所有卡。

Solution

\(\min-\max\)容斥板子题。

\(\min-\max\)容斥是说一个这样的式子:
\[ \max\{S\}=\sum_{T\subset S}(-1)^{|T|+1}\min\{T\} \]
这个式子在期望下成立,在这题\(\min\{S\}\)就表示\(S\)集合中第一张卡出现时间的期望,\(\max\)就是最后一张的期望。

那么显然可以得到:
\[ \min\{S\}=\frac{1}{\sum_{i\in S}p_i} \]
然后范围比较小直接暴力算就好了。

时间复杂度\(O(2^n)\)。

#include<bits/stdc++.h>
using namespace std;
 
void read(int &x) {
    x=0;int f=1;char ch=getchar();
    for(;!isdigit(ch);ch=getchar()) if(ch=='-') f=-f;
    for(;isdigit(ch);ch=getchar()) x=x*10+ch-'0';x*=f;
}
 
void print(int x) {
    if(x<0) putchar('-'),x=-x;
    if(!x) return ;print(x/10),putchar(x%10+48);
}
void write(int x) {if(!x) putchar('0');else print(x);putchar('\n');}

#define lf double

const int maxn = 2e5+10;
const lf eps = 1e-6;

int n;
lf p[maxn],ans;

void dfs(int now,lf sum,int f) {
    if(now==n+1) return ans+=fabs(sum)<eps?0:(lf)f*1.0/sum,void();
    dfs(now+1,sum+p[now],-f);
    dfs(now+1,sum,f);
}

int main() {
    while(scanf("%d",&n)!=EOF) {
        for(int i=1;i<=n;i++) scanf("%lf",&p[i]);
        dfs(1,0,-1);
        printf("%lf\n",ans);ans=0;
    }
    return 0;
}

标签:HDU4336,ch,min,int,max,sum,Collector,Card,getchar
来源: https://www.cnblogs.com/hbyer/p/10515063.html