【BZOJ3450】Easy(期望)

题意:

某一天WJMZBMR在打osu~~~但是他太弱逼了,有些地方完全靠运气:(
我们来简化一下这个游戏的规则
有n次点击要做,成功了就是o,失败了就是x,分数是按comb计算的,连续a个comb就有a*a分,comb就是极大的连续o。
比如ooxxxxooooxxx,分数就是2*2+4*4=4+16=20。
Sevenkplus闲的慌就看他打了一盘,有些地方跟运气无关要么是o要么是x,有些地方o或者x各有50%的可能性,用?号来表示。
比如oo?xx就是一个可能的输入。
那么WJMZBMR这场osu的期望得分是多少呢?
比如oo?xx的话,?是o的话就是oooxx => 9,是x的话就是ooxxx => 4
期望自然就是(4+9)/2 =6.5了

n<=300000

思路:几年前某场联赛模拟的题

显然有一个二维dp[i][j]表示当前到第i位,后缀o的长度为j的期望

对于a[i]=?

[ dp[i][j]=(dp[i+1,j+1]+(j+1)^2-j^2+dp[i+1][0])/2 ]

于是发现j变大1的贡献是线性的2j+1,而期望具有线性的可加性

所以第二维可以省略

设f[i]为当前到第i位的期望,g[i]为当前到第i位后缀o长度的期望

转移类似

 1 #include<cstdio>
 2 #include<cstring>
 3 #include<string>
 4 #include<cmath>
 5 #include<iostream>
 6 #include<algorithm>
 7 #include<map>
 8 #include<set>
 9 #include<queue>
10 #include<vector>
11 using namespace std;
12 typedef long long ll;
13 typedef unsigned int uint;
14 typedef unsigned long long ull;
15 typedef pair<int,int> PII;
16 typedef vector<int> VI;
17 #define fi first
18 #define se second 
19 #define MP make_pair
20 #define N   1100000
21 #define MOD 1000000007
22 #define eps 1e-8 
23 #define pi acos(-1)
24 
25 char a[N];
26 double f[N],g[N];
27 
28 int read()
29 { 
30    int v=0,f=1;
31    char c=getchar();
32    while(c<48||57<c) {if(c=='-') f=-1; c=getchar();}
33    while(48<=c&&c<=57) v=(v<<3)+v+v+c-48,c=getchar();
34    return v*f;
35 }
36 
37 int main()
38 {
39     //freopen("bzoj3450.in","r",stdin);
40     //freopen("bzoj3450.out","w",stdout);
41     int n;
42     scanf("%d",&n);
43     scanf("%s",a+1);
44     for(int i=1;i<=n;i++)
45     {
46         if(a[i]=='x'){f[i]=f[i-1]; g[i]=0;}
47         if(a[i]=='o'){f[i]=f[i-1]+g[i-1]*2+1; g[i]=g[i-1]+1;}
48         if(a[i]=='?'){f[i]=f[i-1]+g[i-1]+0.5; g[i]=(g[i-1]+1)/2;}
49     }
50     printf("%.4lf
",f[n]);
51     return 0;
52 }
原文地址:https://www.cnblogs.com/myx12345/p/9620673.html