Gym - 101190F Foreign Postcards 概率期望

本文探讨了一种涉及邮票翻转的数学期望问题,通过两种不同的算法解决如何计算邮票在特定翻转规则下,最终错误放置在桌面上的平均数量。第一种算法采用前缀和与概率计算相结合的方法,而第二种算法则采用动态规划逆向计算策略。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Fedor is an avid traveler. As a result of his hobby, he has gathered a big collection of postcards from all over the world. Each postcard has a unique picture on the front side and some fields for address information and text on the back side. During one of the parties at Fedor’s house, he decided to show all his of postcards to the guests. To achieve that, he wants to lay them all out on the table. Initially, all of his postcards are arranged in a single stack that Fedor is holding in his hands. Unfortunately, some of the postcards in that stack can be turned incorrectly — upside down. Ideally, Fedor would like all postcards on the table to lie with the picture on top, but looking at every postcard and turning it over individually can be very time-consuming. Instead, he came up with the following process:
1. Let n be the number of postcards remaining in the stack in his hands. Fedor chooses a random number k uniformly between 1 and n and takes top k postcards from the stack.
2. He looks at the topmost postcard among these k postcards. If it is oriented in the wrong way, he turns the whole stack of k postcards upside down together.
3. He then puts these k postcards on the table without any further rotations.
4. If there are still some postcards remaining in the stack in his hands, Fedor goes back to step 1.
Of course, after all the postcards are on the table, there might still be some that lie back side up. What is the expected number of such postcards?
Input
The input consists of a single line of “C” and “W” characters — i-th character corresponds to i-th postcard in the stack, counting from the top of the stack. “C” means that i-th postcard is oriented correctly in the initial stack, and “W” means that i-th postcard is oriented in the wrong way. The number of characters is between 1 and 106 inclusive.
Output
Output one real number — the expected number of incorrectly placed postcards on the table. The absolute or relative error should not exceed 10−9.
Examples
foreign.in foreign.out

CWCC                    1.0 

WWCWCCW           2.333333333333

题解1:

计算每个位置为首的概率乘上以该点为首对应期望 然后在都加起来即可,先预处理,求一下W C 对应的前缀和 和 前缀和的前缀和,在第i个位置若是C 那期望就是 (sumc2[n]-sumc2[i-1]-sumc1[i-1]*(len-i)) / (len-i)/该点为首的概率,很容易我们就会计算得到,第一个点概率为1,第二个为1/n,第三个为1/n+1/(n*(n-1)) = 1/(n-1),......依次类推

#include<iostream>
#include<cstdio>
using namespace std;
const int N=1e6+10;
double sumc1[N],sumc2[N];
double sumw1[N],sumw2[N];
int main()
{
	freopen("foreign.in","r",stdin);
	freopen("foreign.out","w",stdout);
	string s;
	cin>>s;
	int len=s.size();
	if(s[0]=='W') sumw1[0]=1,sumw2[0]=1;
	else sumc1[0]=1,sumc2[0]=1;
	for(int i=1;i<len;i++)
	{
		sumw1[i]=sumw1[i-1];
		if(s[i]=='W') sumw1[i]+=1;
		sumw2[i]+=sumw2[i-1]+sumw1[i];
		
		sumc1[i]+=sumc1[i-1];
		if(s[i]=='C') sumc1[i]+=1;
		sumc2[i]+=sumc2[i-1]+sumc1[i];
	}
	double ans;
	if(s[0]=='W')
		ans=(double)sumc2[len-1]/len;
	else
		ans=(double)sumw2[len-1]/len;
	for(int i=1;i<len;i++)
	{
		double p=(double)1/(len-i+1)/(len-i);
		if(s[i]=='W')
			ans+=(sumc2[len-1]-sumc2[i-1]-sumc1[i-1]*(len-i))*p;
		else
			ans+=(sumw2[len-1]-sumw2[i-1]-sumw1[i-1]*(len-i))*p;
	}
	printf("%.12f\n",ans);
	return 0;
}

题解2:

无敌的佳神还有另一种思路,就是从后往前求 dp[i] 表示 从i开始到最后的期望,每次计算的S W ,就是 每个位置S W到最后的距离 累加起来就可以了,  ans维护一个dp[i]的后缀和  +1太牛逼了  有哪路大神来把这位又可爱又聪明的+咦咦咦带走啊,咋了,你想? 这个题都不会做,你是没有机会的了,死心吧。

#include<iostream>
#include<cstdio>
using namespace std;
const int N=1e6+10;
double dp[N];
int main()
{
	freopen("foreign.in","r",stdin);
	freopen("foreign.out","w",stdout);
	string s;
	cin>>s;
	int len=s.size();
	double sc=0,sw=0,ans=0;
	for(int i=len-1;i>=0;i--)
	{
		if(s[i]=='W')
		{
			dp[i]=(ans+sc)/(len-i);
			sw+=(len-i);
		}
		else
		{
			dp[i]=(ans+sw)/(len-i);
			sc+=(len-i);
		}
		ans+=dp[i]; 
	}
	printf("%.12f\n",dp[0]);
	return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值