[概率期望]
文章目录
- 概率期望
- [Bag of mice](https://codeforces.com/problemset/problem/148/D)
- [Second price auction](http://codeforces.com/problemset/problem/513/C)
- [Need for Pink Slips](http://codeforces.com/problemset/problem/1543/C)
- [Let's Play Osu!](http://codeforces.com/problemset/problem/235/B)
- [Third Month Insanity](http://codeforces.com/problemset/problem/859/D)
- [Beautiful Mirrors](http://codeforces.com/problemset/problem/1265/E)
- [Wish I Knew How to Sort](http://codeforces.com/problemset/problem/1753/C)
- [Flexible String Revisit](http://codeforces.com/problemset/problem/1778/D)
概率期望
- 感觉没有什么好说的。主要是凭感觉和可列无穷大的期望推导加上孟德尔的豌豆就行了。就记录几道题吧!
Bag of mice
题面翻译
袋子里有 w w w 只白鼠和 b b b 只黑鼠 ,A和B轮流从袋子里抓,谁先抓到白色谁就赢。A每次随机抓一只,B每次随机抓完一只之后会有另一只随机老鼠跑出来。如果两个人都没有抓到白色则B赢。A先抓,问A赢的概率。
输入
一行两个数 w , b w,b w,b 。
输出
A赢的概率,误差 1 0 − 9 10^{-9} 10−9 以内。
数据范围
0 ≤ w , b ≤ 1000 0\le w,b\le 1000 0≤w,b≤1000 。
题目描述
The dragon and the princess are arguing about what to do on the New Year’s Eve. The dragon suggests flying to the mountains to watch fairies dancing in the moonlight, while the princess thinks they should just go to bed early. They are desperate to come to an amicable agreement, so they decide to leave this up to chance.
They take turns drawing a mouse from a bag which initially contains
If there are no more mice in the bag and nobody has drawn a white mouse, the dragon wins. Mice which jump out of the bag themselves are not considered to be drawn (do not define the winner). Once a mouse has left the bag, it never returns to it. Every mouse is drawn from the bag with the same probability as every other one, and every mouse jumps out of the bag with the same probability as every other one.
输入格式
The only line of input data contains two integers
输出格式
Output the probability of the princess winning. The answer is considered to be correct if its absolute or relative error does not exceed
样例 #1
样例输入 #1
1 3
样例输出 #1
0.500000000
样例 #2
样例输入 #2
5 5
样例输出 #2
0.658730159
提示
Let’s go through the first sample. The probability of the princess drawing a white mouse on her first turn and winning right away is 1/4. The probability of the dragon drawing a black mouse and not winning on his first turn is 3/4 * 2/3 = 1/2. After this there are two mice left in the bag — one black and one white; one of them jumps out, and the other is drawn by the princess on her second turn. If the princess’ mouse is white, she wins (probability is 1/2 * 1/2 = 1/4), otherwise nobody gets the white mouse, so according to the rule the dragon wins.
题解
记录dp[i][j]为抓了i只黑鼠j只白鼠的概率则当下状态可转移到dp[i+2][j+1]和dp[i+3][j],初始dp[0][0]=1。将每个状态的概率乘A在当前状态抓到白鼠的概率求和就是答案。
代码
#include<iostream>
using namespace std;
const int N=1e3+10;
double dp[N][N],ans,esp=1e-13;
int w,b;
int main(){
scanf("%d%d",&w,&b);
dp[0][0]=1+esp;
for(int i=0;i<=b;i++){
for(int j=0;j<=w;j++){
double x=w-j,y=b-i;
dp[i+2][j+1]+=dp[i][j]*(y/(x+y))*((y-1)/(x+y-1))*(x/(x+y-2));
dp[i+3][j]+=dp[i][j]*(y/(x+y))*((y-1)/(x+y-1))*((y-2)/(x+y-2));
if((i+j)%3==0){
if(x+y!=0)
ans+=dp[i][j]*(x/(x+y));
}
}
}
printf("%.12lf",ans);
}
Second price auction
题面翻译
有 n n n 个人竞拍一件商品,第 i i i 个人将从 [ L i , R i ] [L_i,R_i] [Li,Ri] 中 等概率地选择一个数作为出价,求第二高的出价的期望。
题目描述
Nowadays, most of the internet advertisements are not statically linked to a web page. Instead, what will be shown to the person opening a web page is determined within 100 milliseconds after the web page is opened. Usually, multiple companies compete for each ad slot on the web page in an auction. Each of them receives a request with details about the user, web page and ad slot and they have to respond within those 100 milliseconds with a bid they would pay for putting an advertisement on that ad slot. The company that suggests the highest bid wins the auction and gets to place its advertisement. If there are several companies tied for the highest bid, the winner gets picked at random.
However, the company that won the auction does not have to pay the exact amount of its bid. In most of the cases, a second-price auction is used. This means that the amount paid by the company is equal to the maximum of all the other bids placed for this ad slot.
Let’s consider one such bidding. There are
Determine the expected value that the winner will have to pay in a second-price auction.
输入格式
The first line of input contains an integer number
This problem doesn’t have subproblems. You will get 8 points for the correct submission.
输出格式
Output the answer with absolute or relative error no more than
样例 #1
样例输入 #1
3
4 7
8 10
5 5
样例输出 #1
5.7500000000
样例 #2
样例输入 #2
3
2 5
3 4
1 6
样例输出 #2
3.5000000000
提示
Consider the first example. The first company bids a random integer number of microdollars in range
题解
设dp[i][j][k]为前j个人游有k个人选的价格至少为i。考虑枚举i这一维,即每个i单独算。(应该也可以倒序枚k举省略j这一维,但没打)每个人选价格至少为i的概率为max(r-max(l,i)+1,0)/(r-l+1)。
最后记f[i]为第二高的价格至少为i的概率。f[i]-f[i+1]就是恰好第二高的价格为i的概率。
代码
#include<iostream>
#include<algorithm>
#include<cmath>
using namespace std;
const int N=15;
const int M=10005;
int n,l[N],r[N],m;
double dp[N][N],ans,f[M];
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d%d",&l[i],&r[i]);
m=max(m,r[i]);
}
dp[0][0]=1;
for(int i=1;i<=m;i++){
for(int j=1;j<=n;j++){
double pp=1.0*max(r[j]-max(l[j],i)+1,0)/(r[j]-l[j]+1);
for(int k=1;k<=j;k++)
dp[j][k]=dp[j-1][k-1]*pp+dp[j-1][k]*(1-pp);
dp[j][0]=dp[j-1][0]*(1.0-pp);
}
for(int j=2;j<=n;j++)
f[i]+=dp[n][j];
}
for(int i=1;i<=m;i++)
ans+=(f[i]-f[i+1])*i;
printf("%.12lf",ans);
}
Need for Pink Slips
题面翻译
在完成一项游戏任务后,你得到了一次抽奖的机会。
初始时,抽奖只有三种有效奖励:Cash Slip,Impound Strike Release Marker 和 Pink Slip,初始时你抽到它们的概率为
c
,
m
,
p
c,m,p
c,m,p,同时抽奖还有一个不稳定性
v
v
v。你将会一直抽奖直到抽中一张 Pink Slip,假设在一次抽奖中你抽到了某个被抽中概率为
a
a
a 的奖励,接下来:
- 如果你抽中的是 Pink Slip,停止抽奖。
- 否则,如果 a ≤ v a\leq v a≤v,抽中这种奖励的概率变为 0 0 0,且这种奖励将失效,并永远不会出现在接下来的抽奖中,这种奖励被抽到的概率 a a a 将平均分配给剩下的还有效的奖励的概率中。
- 否则, a a a 将减少 v v v,减少的概率同样将平均分配给剩下的除了这种奖励外还有效的奖励的概率中。
求出期望的抽奖次数。
T
T
T 组数据。
1
≤
T
≤
10
;
0
<
c
,
m
,
p
<
1
;
c
+
m
+
p
=
1
;
0.1
≤
v
≤
0.9
;
1\leq T\leq10;0<c,m,p<1;c+m+p=1;0.1\leq v\leq0.9;
1≤T≤10;0<c,m,p<1;c+m+p=1;0.1≤v≤0.9;
c
,
m
,
p
,
v
c,m,p,v
c,m,p,v 最多只有
4
4
4 位小数。
你的答案与标准答案的相对或绝对误差不能超过
1
0
−
6
10^{-6}
10−6。
如果你无法理解抽奖的过程,下面是关于抽奖的一些例子:
- 如果 ( c , m , p ) = ( 0.2 , 0.1 , 0.7 ) , v = 0.1 (c,m,p)=(0.2,0.1,0.7),v=0.1 (c,m,p)=(0.2,0.1,0.7),v=0.1,且你抽到了 Cash Slip,抽奖后 ( c , m , p ) = ( 0.1 , 0.15 , 0.75 ) (c,m,p)=(0.1,0.15,0.75) (c,m,p)=(0.1,0.15,0.75)。
- 如果 ( c , m , p ) = ( 0.1 , 0.2 , 0.7 ) , v = 0.2 (c,m,p)=(0.1,0.2,0.7),v=0.2 (c,m,p)=(0.1,0.2,0.7),v=0.2,且你抽到了 Cash Slip,抽奖后 ( c , m , p ) = ( 0 , 0.25 , 0.75 ) (c,m,p)=(0,0.25,0.75) (c,m,p)=(0,0.25,0.75),Cash Slip 将失效。
- 如果 ( c , m , p ) = ( 0.2 , 0 , 0.8 ) , v = 0.1 (c,m,p)=(0.2,0,0.8),v=0.1 (c,m,p)=(0.2,0,0.8),v=0.1,且你抽到了 Cash Slip,抽奖后 ( c , m , p ) = ( 0.1 , 0 , 0.9 ) (c,m,p)=(0.1,0,0.9) (c,m,p)=(0.1,0,0.9)。
- 如果 ( c , m , p ) = ( 0.1 , 0 , 0.9 ) , v = 0.2 (c,m,p)=(0.1,0,0.9),v=0.2 (c,m,p)=(0.1,0,0.9),v=0.2,且你抽到了 Cash Slip,抽奖后 ( c , m , p ) = ( 0 , 0 , 1 ) (c,m,p)=(0,0,1) (c,m,p)=(0,0,1),Cash Slip 将失效。
题目描述
After defeating a Blacklist Rival, you get a chance to draw
- If the item was a Pink Slip, the quest is over, and you will not play any more races.
- Otherwise,
- If
, the probability of the item drawn becomes and the item is no longer a valid item for all the further draws, reducing by . Moreover, the reduced probability is distributed equally among the other remaining valid items. - If
, the probability of the item drawn reduces by and the reduced probability is distributed equally among the other valid items.
- If
For example,
- If
and , after drawing Cash, the new probabilities will be . - If
and , after drawing Cash, the new probabilities will be . - If
and , after drawing Cash, the new probabilities will be . - If
and , after drawing Cash, the new probabilities will be .
You need the cars of Rivals. So, you need to find the expected number of races that you must play in order to draw a pink slip.
输入格式
The first line of input contains a single integer
The first and the only line of each test case contains four real numbers
Additionally, it is guaranteed that each of
输出格式
For each test case, output a single line containing a single real number — the expected number of races that you must play in order to draw a Pink Slip.
Your answer is considered correct if its absolute or relative error does not exceed
Formally, let your answer be
样例 #1
样例输入 #1
4
0.2 0.2 0.6 0.2
0.4 0.2 0.4 0.8
0.4998 0.4998 0.0004 0.1666
0.3125 0.6561 0.0314 0.2048
样例输出 #1
1.532000000000
1.860000000000
5.005050776521
4.260163673896
提示
For the first test case, the possible drawing sequences are:
- P with a probability of
; - CP with a probability of
; - CMP with a probability of
; - CMMP with a probability of
; - MP with a probability of
; - MCP with a probability of
; - MCCP with a probability of
.
So, the expected number of races is equal to
- P with a probability of
; - CP with a probability of
; - CMP with a probability of
; - MP with a probability of
; - MCP with a probability of
.
So, the expected number of races is equal to
题解
按照题面暴力枚举,可能dfs比dp要好写一点?
因为最后抽中要一次所以最后要加一,也可以像这里写的一样初始就需一次
代码
#include<iostream>
#include<cmath>
using namespace std;
int n,t;
double ans,v,esp=1e-9;
void dfs(double a,double b,double c,double p,int cnt){
ans+=c*p*cnt;
if(a){
if(a-v>=esp){
if(b)
dfs(a-v,b+v/2,c+v/2,p*a,cnt+1);
else
dfs(a-v,0,c+v,p*a,cnt+1);
}
else{
if(b)
dfs(0,b+a/2,c+a/2,p*a,cnt+1);
else
dfs(0,0,c+a,p*a,cnt+1);
}
}
if(b){
if(b-v>=esp){
if(a)
dfs(a+v/2,b-v,c+v/2,p*b,cnt+1);
else
dfs(0,b-v,c+v,p*b,cnt+1);
}
else{
if(a)
dfs(a+b/2,0,c+b/2,p*b,cnt+1);
else
dfs(0,0,c+b,p*b,cnt+1);
}
}
}
int main(){
double c,m,p;
scanf("%d",&t);
while(t--){
scanf("%lf%lf%lf%lf",&c,&m,&p,&v);
ans=0;
dfs(c,m,p,1.0,1);
printf("%.12lf\n",ans);
}
}
Let’s Play Osu!
题面翻译
你在玩一个叫做Osu的游戏(某音游)!我们来简化一下游戏规则。一局游戏中需要点击n次。每一次点击有两种结果:正确或失误。我们定义正确为符号"O",失误为"X",那么整局游戏可以被写成一个长度为n的由字符"X"或"O"组成的字符串。
用这个字符串你可以用以下的方法计算游戏的得分:对于一个极大的连续的"O"连击,将连击的次数的平方加入到总得分中(即连续的"O"的个数的平方)。举例说明,如果你的游戏序列为"OOXOOOXXOO",那么极大连续的“O”连击共有三个:“OO”,“OOO”,“OO”,所以你的总得分为 2^2 + 3^2 + 2^2= 17 。如果整局游戏里没有一次成功的点击那么总得分就为 0 。
你现在知道了第i次( 1<=i<=n )点击成功的概率为 p_i,换句话说,字符串中第i个字符有 p_i 的概率成为"O",有 1-p_i 的概率成为"X",你的任务是算出你游戏总得分的期望值。
输入输出格式
输入格式:
第一行包含一个整数表示点击的次数 n ( 1<=n<=10^5 ) 第二行包含 n 个由空格间隔开的实数p_1,p_2,…,p_n ( 0<=p_i<=1 )
输入的 p_i 最多为六位小数
输出格式:
输出一个实数——你游戏的期望得分。你的答案必须与标准答案的误差不超过 10^{-6}
样例一说明
3位字符串一共有8种不同的情况。每一种出现的概率为0.125
所以期望得分是 (9+4+2+1+4+1+1)/8=2.75
感谢@凄魉 提供的翻译
题目描述
You’re playing a game called Osu! Here’s a simplified version of it. There are
Using the play sequence you can calculate the score for the play as follows: for every maximal consecutive "O"s block, add the square of its length (the number of characters “O”) to the score. For example, if your play can be encoded as “OOXOOOXXOO”, then there’s three maximal consecutive "O"s block “OO”, “OOO”, “OO”, so your score will be $ 2{2}+3{2}+2^{2}=17
You know that the probability to click the
输入格式
The first line contains an integer
There will be at most six digits after the decimal point in the given
输出格式
Print a single real number — the expected score for your play. Your answer will be considered correct if its absolute or relative error does not exceed
样例 #1
样例输入 #1
3
0.5 0.5 0.5
样例输出 #1
2.750000000000000
样例 #2
样例输入 #2
4
0.7 0.2 0.1 0.9
样例输出 #2
2.489200000000000
样例 #3
样例输入 #3
5
1 1 1 1 1
样例输出 #3
25.000000000000000
提示
For the first example. There are 8 possible outcomes. Each has a probability of 0.125.
- “OOO”
; - “OOX”
; - “OXO”
$ 1{2}+1{2}=2 $ ; - “OXX”
; - “XOO”
; - “XOX”
; - “XXO”
; - “XXX”
.
So the expected score is
题解
考虑每个位置上的贡献。长度从i变为i+1时,分值的变化量为(i+1)2-i2=2i+1。设P(i,j)只考虑前i位,以第i位结尾的连续极大‘O’段长度为j的概率,dp[i]为只考虑前i位,以第i位结尾的连续极大‘O’段的长度的期望;
则
d
p
i
+
1
=
∑
j
=
0
i
(
j
+
1
)
×
P
(
i
+
1
,
j
+
1
)
dp_{i+1}=\sum_{j=0}^{i}(j+1) \times P(i+1,j+1)
dpi+1=∑j=0i(j+1)×P(i+1,j+1)
~~~~~~~~~~~~~~~~
=
∑
j
=
0
i
(
j
+
1
)
×
P
(
i
+
1
,
j
+
1
)
=\sum_{j=0}^{i}(j+1) \times P(i+1,j+1)
=∑j=0i(j+1)×P(i+1,j+1)
~~~~~~~~~~~~~~~~
=
∑
j
=
0
i
j
×
P
(
i
+
1
,
j
+
1
)
+
∑
j
=
0
i
P
(
i
+
1
,
j
+
1
)
=\sum_{j=0}^{i}j \times\ P(i+1,j+1)+\sum_{j=0}^{i}P(i+1,j+1)
=∑j=0ij× P(i+1,j+1)+∑j=0iP(i+1,j+1)
~~~~~~~~~~~~~~~~
=
∑
j
=
0
i
j
×
P
(
i
,
j
)
×
p
i
+
p
i
=\sum_{j=0}^{i}j \times P(i,j) \times pi+pi
=∑j=0ij×P(i,j)×pi+pi
~~~~~~~~~~~~~~~~
=
p
i
×
∑
j
=
0
i
j
×
P
(
i
,
j
)
+
p
i
=pi \times\sum_{j=0}^{i}j \times\ P(i,j)+pi
=pi×∑j=0ij× P(i,j)+pi
~~~~~~~~~~~~~~~~
=
p
i
×
(
d
p
i
+
1
)
=pi \times(dp_i+1)
=pi×(dpi+1)
因为:
∑
j
=
0
i
P
(
i
+
1
,
j
+
1
)
=
p
i
×
∑
j
=
0
i
P
(
i
,
j
)
=
p
i
\sum_{j=0}^{i}P(i+1,j+1)=pi \times\sum_{j=0}^{i}P(i,j)=pi
∑j=0iP(i+1,j+1)=pi×∑j=0iP(i,j)=pi
最后:第i位的期望为
p
i
×
(
2
×
d
p
i
−
1
+
1
)
pi \times(2\times dp_{i-1}+1)
pi×(2×dpi−1+1)
代码
#include<iostream>
using namespace std;
int n;
double p,dp[100005],ans;
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%lf",&p);
dp[i]=p*(dp[i-1]+1);
ans+=p*(dp[i-1]*2+1);
}
printf("%.12lf",ans);
}
Third Month Insanity
题面翻译
有 2n个人要进行比赛,每次2i与2i+1号人进行比赛 ( i ∈ [ 0 , 2 n − 1 ) ) (i\in [0,2^{n-1})) (i∈[0,2n−1))。这一轮中赢的人进入下一轮。下一轮比赛的时候把进入这一轮的人按编号排好,仍然是像之前那样相邻的进行一次比赛。最后只剩下一个人。
数据给出对于 x , y x,y x,y, x x x打赢 y y y的概率。
第 i i i轮比赛会角逐出2n-i个赢家。我们要在比赛开始前,猜每轮的赢家(一轮的赢家一定要是上一轮的赢家)。第i轮每猜中一个赢家就会得到2i-1的得分。
求最大的期望得分。 n ⩽ 6 n \leqslant 6 n⩽6
题目描述
The annual college sports-ball tournament is approaching, which for trademark reasons we’ll refer to as Third Month Insanity. There are a total of
Every year the office has a pool to see who can create the best bracket. A bracket is a set of winner predictions for every game. For games in the first round you may predict either team to win, but for games in later rounds the winner you predict must also be predicted as a winner in the previous round. Note that the bracket is fully constructed before any games are actually played. Correct predictions in the first round are worth
For every pair of teams in the league, you have estimated the probability of each team winning if they play against each other. Now you want to construct a bracket with the maximum possible expected score.
输入格式
Input will begin with a line containing
输出格式
Print the maximum possible expected score over all possible brackets. Your answer must be correct to within an absolute or relative error of
Formally, let your answer be .
样例 #1
样例输入 #1
2
0 40 100 100
60 0 40 40
0 60 0 45
0 60 55 0
样例输出 #1
1.75
样例 #2
样例输入 #2
3
0 0 100 0 100 0 0 0
100 0 100 0 0 0 100 100
0 0 0 100 100 0 0 0
100 100 0 0 0 0 100 100
0 100 0 100 0 0 100 0
100 100 100 100 100 0 0 0
100 0 100 0 0 100 0 0
100 0 100 0 100 100 100 0
样例输出 #2
12
样例 #3
样例输入 #3
2
0 21 41 26
79 0 97 33
59 3 0 91
74 67 9 0
样例输出 #3
3.141592
提示
In the first example, you should predict teams 1 1 1 and 4 4 4 to win in round 1 1 1 , and team 1 1 1 to win in round 2 2 2 . Recall that the winner you predict in round 2 2 2 must also be predicted as a winner in round 1 1 1
题解
设dp[i][j]为选手i赢得第j轮比赛的胜利的概率,设k为选手i当前这轮可能的对手,g[i][k]为i战胜k的概率,则dp[i][j]=dp[i][j-1]*∑dp[k][j-1]*g[i][k]。设e[i][j]为最优预测中选手i赢得j轮比赛的期望,则dp[i][j]=e[i][j-1]+max{e[k][j-1]}+dp[i][j]*2j-1.答案为max{e[i][n]}。
代码
#include<iostream>
using namespace std;
int n,m;
double g[70][70],dp[70][10],e[70][10],ans;
int main(){
scanf("%d",&n);
m=1<<n;
for(int i=0;i<m;i++)
for(int j=0;j<m;j++){
scanf("%lf",&g[i][j]);
g[i][j]/=100;
}
for(int i=0;i<m;i++)
dp[i][0]=1;
for(int j=1;j<=n;j++)
for(int i=0;i<m;i++){
int k=(1<<j),fi=i/k*k;
for(int o=0;o<k;o++)
if(fi+o!=i&&(fi+o)/(k/2)!=i/(k/2))
dp[i][j]+=dp[o+fi][j-1]*g[i][fi+o];
dp[i][j]*=dp[i][j-1];
}
for(int j=1;j<=n;j++)
for(int i=0;i<m;i++){
int k=(1<<j),fi=i/k*k;
for(int o=0;o<k;o++)
if(fi+o!=i&&(fi+o)/(k/2)!=i/(k/2))
e[i][j]=max(e[i][j],e[fi+o][j-1]);
e[i][j]+=e[i][j-1]+dp[i][j]*(1<<(j-1));
}
for(int i=0;i<m;i++)
ans=max(ans,e[i][n]);
printf("%.12lf",ans);
}
Beautiful Mirrors
题面翻译
题目描述:
小C有 N N N个从编号分别为 1 1 1到 N N N的镜子。她每天都会问一面镜子:“我漂亮吗?”而对于第 i i i面镜子,有 p i 100 p_i \over100 100pi ( 1 ≤ i ≤ n ) (1≤i≤n) (1≤i≤n)的概率告诉小C很漂亮。
她从第一面镜子开始,一个接一个的问镜子。每一天,对于她问的第 i i i个镜子,有两种情况:
- 如果第 i i i个镜子告诉小C她很漂亮:若此时 i = n i=n i=n,则小C就会开心到极点,停止对镜子的询问。否则,她第二天就会询问第 i + 1 i+1 i+1个镜子
- 如果第 i i i个镜子并没有告诉小C她很漂亮,她就会很伤心,第二天重新从第 1 1 1个镜子开始询问。
你需要计算小C询问完所有镜子后开心到极点的期望天数。若期望天数可被表示为最简分数 p q p \over q qp,则你需要输出的是 p ⋅ q − 1 ( m o d p \cdot q^{-1} (mod p⋅q−1(mod 998244353 ) 998244353) 998244353)。
输入格式
第一行输入一个整数 n n n ( 1 ≤ n ≤ 2 ⋅ 1 0 5 ) ( 1\le n\le 2\cdot 10^5) (1≤n≤2⋅105),表示镜子的个数。
第二行输入 n n n个整数 p 1 , p 2 , … , p n p_1, p_2 , \ldots , p_n p1,p2,…,pn ( 1 ≤ p i ≤ 100 ) (1 \leq p_i \leq 100) (1≤pi≤100)。
输出格式
输出一个整数,为答案模 998244353 998244353 998244353的结果
说明/提示
在第一个样例,只有一个镜子,并且它有 1 2 1 \over 2 21的概率告诉小C她很漂亮。所以,让小C开心到极点的期望天数是2天
题目描述
Creatnx has
Creatnx asks the mirrors one by one, starting from the
- The
-th mirror tells Creatnx that he is beautiful. In this case, if Creatnx will stop and become happy, otherwise he will continue asking the -th mirror next day; - In the other case, Creatnx will feel upset. The next day, Creatnx will start asking from the
-st mirror again.
You need to calculate the expected number of days until Creatnx becomes happy.
This number should be found by modulo
输入格式
The first line contains one integer
The second line contains
输出格式
Print the answer modulo
样例 #1
样例输入 #1
1
50
样例输出 #1
2
样例 #2
样例输入 #2
3
10 20 50
样例输出 #2
112
提示
In the first test, there is only one mirror and it tells, that Creatnx is beautiful with probability
题解
这就是一道可列无穷大的期望的题。设pi为每面镜子的概率,dp[i]为问完第i面镜子所需的时间。
d
p
i
=
p
i
×
(
d
p
i
−
1
+
1
)
+
(
1
−
p
i
)
×
(
d
p
i
−
1
+
1
+
d
p
i
)
dp_i=p_i\times (dp_{i-1}+1)+(1-p_i)\times(dp_{i-1}+1+dp_i)
dpi=pi×(dpi−1+1)+(1−pi)×(dpi−1+1+dpi)
化简得
d
p
i
=
d
p
i
−
1
+
1
p
i
dp_i=\frac{dp_{i-1}+1}{p_i}
dpi=pidpi−1+1
dp[n]即为所求。
代码
#include<iostream>
using namespace std;
typedef long long ll;
const ll mod=998244353;
int n;
ll p,dp;
ll fpow(ll a,ll b){
ll res=1;
while(b){
if(b&1)
res=res*a%mod;
a=a*a%mod;
b>>=1;
}
return res;
}
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%lld",&p);
if(p==0){
printf("0");
return 0;
}
dp=fpow(p,mod-2)*(dp+1)%mod*100%mod;
}
printf("%lld",dp);
}
Wish I Knew How to Sort
题面翻译
给定一个长度为 n n n 的 01 序列 a a a 和一种操作,你需要用这种操作将序列从小到大排序。
操作如下:
- 等概率随机选取两个位置 i , j ( i < j ) i,j\ (i<j) i,j (i<j),若 a i > a j a_i>a_j ai>aj,则交换 a i , a j a_i,a_j ai,aj。
注意:当 a i ≤ a j a_i\le a_j ai≤aj 时,交换失败,也算作一次操作。
请你求出操作被执行的 期望次数。对 998244353 取模。 1 ≤ n ≤ 2 × 1 0 5 , a i ∈ { 0 , 1 } 1\le n\le2\times 10^5,\ a_i\in \{0,1\} 1≤n≤2×105, ai∈{0,1}。
题目描述
You are given a binary array
- Choose two random indices
and such that . Indices are chosen equally probable among all pairs of indices such that . - If
, then swap elements and .
What is the expected number of such operations you will perform before the array becomes sorted?
It can be shown that the answer can be expressed as an irreducible fraction
输入格式
Each test contains multiple test cases. The first line contains the number of test cases
The first line of each test case contains an integer
The second line of each test case contains
It’s guaranteed that sum of
输出格式
For each test case print one integer — the value
样例 #1
样例输入 #1
3
3
0 1 0
5
0 0 1 1 1
6
1 1 1 0 0 1
样例输出 #1
3
0
249561107
提示
Consider the first test case. If the pair of indices
In the second test case the array is already sorted so the expected number of operations is zero.
In the third test case the expected number of operations equals to
题解
好!枚举求每一次有用的交换的期望。设最终左边有s个0,那么
前s个数中有x个1就是需要交换的个数。设f[i]为还剩下i个数调整一对的期望。
设p为概率,f为期望,则有:
f
i
=
p
i
×
1
+
(
1
−
p
i
)
×
(
f
i
+
1
)
f_i=p_i\times 1+(1-p_i)\times (f_i+1)
fi=pi×1+(1−pi)×(fi+1)
化简得
f
i
=
1
p
i
f_i=\frac{1}{p_i}
fi=pi1,又因为
p
=
i
2
C
n
2
p=\frac{i^2}{C_n^2}
p=Cn2i2因为有i*i对有用的交换
所以
a
n
s
=
∑
i
=
1
x
f
i
=
C
n
2
∑
i
=
1
x
1
i
2
ans=\sum_{i=1}^xf_i=C_n^2\sum_{i=1}^x\frac{1}{i^2}
ans=∑i=1xfi=Cn2∑i=1xi21
代码
#include<iostream>
using namespace std;
typedef long long ll;
const ll mod=998244353;
const int N=2e5+5;
ll ans;
ll fpow(ll a,ll b){
ll res=1;
while(b){
if(b&1)
res=res*a%mod;
a=a*a%mod;
b>>=1;
}
return res;
}
int main(){
int n,a[N],s,x,t;
scanf("%d",&t);
while(t--){
ans=s=x=0;
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
if(a[i]==0)
s++;
}
for(int i=1;i<=s;i++)
if(a[i]==1)
x++;
for(ll i=1;i<=x;i++)
ans=(ans+fpow(i*i,mod-2))%mod;
printf("%lld\n",ans*n%mod*(n-1)%mod*fpow(2,mod-2)%mod);
}
}
Flexible String Revisit
题面翻译
给出两个长度均为 n ( n ≤ 1 0 6 ) n(n\leq 10^6) n(n≤106) 的 01 串 S S S 和 T T T
每次随机将 S S S 中的某一位取反
问:第一次 S = T S = T S=T 时操作次数的期望
题目描述
You are given two binary strings
- An index
( ) is chosen uniformly at random. The character will be flipped. That is, if is , it becomes , and if is , it becomes .
What is the expected number of moves required to make both strings equal for the first time?
A binary string is a string, in which the character is either
输入格式
The first line contains a single integer
The first line of each test case contains a single integer
The second line of each test case contains the binary string
The third line of each test case contains the binary string
It is guaranteed that the sum of
输出格式
For each test case, output a single line containing the expected number of moves modulo
Formally, let
样例 #1
样例输入 #1
4
1
0
1
2
00
00
4
1000
1110
5
01001
10111
样例输出 #1
1
0
665496254
665496277
提示
In the first test case, index
The strings
The expected number of moves for the third and fourth test cases are
题解
和上道题思路差不多,这里主要推一下式子。
设f[i]为有i对有需要取反的的时候减少一对的期望次数。
f
i
=
1
+
(
1
−
i
n
)
×
(
f
i
+
f
i
+
1
)
f_i=1+(1-\frac{i}{n})\times(f_i+f_{i+1})
fi=1+(1−ni)×(fi+fi+1)
化简得
i
n
f
i
=
1
+
(
1
−
i
n
)
f
i
+
1
\frac{i}{n}f_i=1+(1-\frac{i}{n})f_{i+1}
nifi=1+(1−ni)fi+1
f
0
=
0
,
f
n
=
1
f_0=0,f_n=1
f0=0,fn=1,但是i要做除数,所以从n倒推回1。
f
i
=
n
i
+
(
n
i
−
1
)
f
i
+
1
f_i=\frac{n}{i}+(\frac{n}{i}-1)f_{i+1}
fi=in+(in−1)fi+1
代码
#include<iostream>
using namespace std;
const int N=1e6+5;
typedef long long ll;
const ll mod=998244353;
ll fpow(ll a,ll b){
ll res=1;
while(b){
if(b&1)
res=res*a%mod;
a=a*a%mod;
b>>=1;
}
return res;
}
int t,n,ai[N],bi[N];
ll dp[N];
char c;
ll ans,x;
int main(){
scanf("%d",&t);
while(t--){
ans=x=0;
scanf("%d",&n);
for(int i=1;i<=n;i++){
cin>>c;
ai[i]=c-'0';
}
for(int i=1;i<=n;i++){
cin>>c;
bi[i]=c-'0';
}
for(int i=1;i<=n;i++)
if(ai[i]!=bi[i])
x++;
dp[n]=1;
if(x>=n)
ans++;
for(int i=n-1;i>=1;i--){
dp[i]=(dp[i+1]*(n-i)+n)%mod*fpow(i,mod-2)%mod;
if(x>=i)
ans=(ans+dp[i])%mod;
}
printf("%lld\n",ans);
}
}
var code = “e001027c-a1de-47b2-8a71-8c230afce8b3”
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 使用C#创建一个MCP客户端
· ollama系列1:轻松3步本地部署deepseek,普通电脑可用
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· 按钮权限的设计及实现