您的位置:首页 > 其它

ZOJ_3551_Bloodsucker

2015-08-04 22:40 246 查看
Bloodsucker

Time Limit: 2 Seconds
Memory Limit: 65536 KB

In 0th day, there are n-1 people and 1 bloodsucker. Every day, two and only two of them meet. Nothing will happen if they are of the same species, that is, a people meets a people or a bloodsucker meets a bloodsucker. Otherwise, people may be
transformed into bloodsucker with probability p. Sooner or later(D days), all people will be turned into bloodsucker. Calculate the mathematical expectation of
D.

Input

The number of test cases (T, T ≤ 100) is given in the first line of the input. Each case consists of an integer
n and a float number p (1 ≤ n < 100000, 0 <
p ≤ 1, accurate to 3 digits after decimal point), separated by spaces.

Output

For each case, you should output the expectation(3 digits after the decimal point) in a single line.

Sample Input

1
2 1

Sample Output

1.000


Author: WU, Yingxin

Contest: ZOJ Monthly, October 2011

第一个概率期望dp。

这个问题卡了好久,因为其实一直没搞清楚状态之间的关系。

知道概率正推期望反推可是却是没搞清楚推什么。

事实上,我觉得有些还是应该明确。

这个题目求的http://blog.csdn.net/zapdt2是期望,从1个吸血鬼到n个吸血鬼的时间期望。

这里dp[i](我写的ex[i])表示的应该准确的说是i个吸血鬼到n个吸血鬼的时间期望

这样就好理解多了。

因此dp
=0这个初始状态也非常好想,因为n个吸血鬼的状态到n个吸血鬼的状态不需要时间

而所求就应该是dp[1]的值,因为dp[1]就是1个吸血鬼到n个吸血鬼的时间期望,与问题相同

然后根据问题描述吸血鬼总是一个一个增加的要么不增加

所以dp[i]=p变*dp[i+1]+p不变*dp[i]+1

p变=2*i*(n-i)/n/(n-1)*p

化简可得dp[i]和dp[i+1]的关系

还有一种感觉不是很严密的想法

可以求出每天dp[i]到dp[i+1]的概率,那么在这两种状态间转化的时间期望应该是1/那个概率

我觉得这个题目应该是满足了不少苛刻的条件,比如每次转变间没有干扰等等

使得这两种想法的表达式是相同的。

另外这个问题还可以用期望最原始的形式,但是因为概率会变成无穷级数,因此需要错位相减求和

结果也一致。

下面代码中其实n=1的情况判断多余了,去掉也可以

甚至数组也可以不开……直接一个变量刷过去就好了……

#include <iostream>
#include <stdio.h>
using namespace std;

const int M=1e5+5;
double dp[M];

int main()
{
int t;
int n;
double p;
scanf("%d",&t);
while(t--)
{
scanf("%d%lf",&n,&p);
if(n==1)
{
printf("0.000\n");
continue;
}

dp[n-1]=0;
for(int i=n-2;i>=0;i--)
{
dp[i]=dp[i+1]+(double)n*(n-1)/2/(i+1)/(n-i-1)/p;
}
printf("%.3lf\n",dp[0]);
}
return 0;
}



内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: