我是靠谱客的博主 沉静美女,最近开发中收集的这篇文章主要介绍Gym - 101606F-Flipping Coins 概率DP,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

题意:

给出n个硬币,初始时,n个硬币都是正面朝下的。现在你有k次机会将硬币投掷到空中,问你k次投掷后硬币正面朝上的个数的期望是多少

题解:

我们设DP[i][j] 表示 i 次 投掷后有j个硬币正面朝上的概率

最后的答案为∑(DP[k][i] * i)

转移方程为: DP[i+1][j] = DP[i][j] * 0.5              选择一个反面的投掷且投掷结果为反面

                        DP[i+1][j+1] = DP[i][j] * 0.5          选择一个反面的投掷且投掷结果为正面

需要注意的是

                        当j == n时有:

                        DP[i+1][n] = DP[i][n]*0.5                只能选一个正面的投掷,且投掷的结果为正面

                        DP[i+1][n-1] = DP[i][n] * 0.5      因为必须投掷k次,所以当已经全为正面的时候,

                                                                                         有1/2的概率使得一个正面的变成反面

代码

#include<bits/stdc++.h>
using namespace std;
const int maxn = 500;
double dp[maxn][maxn];
double solve(int n,int k) {
memset(dp,0,sizeof(dp));
dp[0][0] = 1;
for(int i=0;i<k;i++) {
for(int j=0;j<n;j++) {
dp[i+1][j] += dp[i][j] * 0.5;
dp[i+1][j+1] += dp[i][j] * 0.5;
}
dp[i+1][n] += dp[i][n] * 0.5;
dp[i+1][n-1] += dp[i][n] * 0.5;
}
double ans = 0;
for(int i=1;i<=n;i++) ans += dp[k][i] * i;
return ans;
}
int main()
{
int n,k;
while(~scanf("%d%d",&n,&k))
{
printf("%.6fn",solve(n,k));
}
return 0;
}

最后

以上就是沉静美女为你收集整理的Gym - 101606F-Flipping Coins 概率DP的全部内容,希望文章能够帮你解决Gym - 101606F-Flipping Coins 概率DP所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(35)

评论列表共有 0 条评论

立即
投稿
返回
顶部