概率 & 期望 DP 总结

概率 & 期望 DP 总结


前言

概率 & 期望 DP 的题目一般都较为明显,通常会直接指出需要你求的概率或期望值。

虽然这类题目是依赖于概率论,但实际上,通常概率或期望 DP 的状态、决策、转移是我们通过自己的认知和性质的分析就可以得出的,所以平时并不需要特别的畏惧概率或期望 DP。


概率 DP

概述

我们通常依照题目要求定义出状态,然后使用递推来从初始向结果转移,这类 DP 通常只是经过了概率论只是的包装。

例题

HDU - 1203

链接

HDUVJudge

分析

非常基础的一题(不过题意有点难读),如果直接按“至少一份 offer 的最大概率”来 DP,这肯定会十分麻烦,那么我们就运用平日里数学中学过的容斥原理,把“至少一份 offer 的最大概率”转换为“1 - 至多零份 offer 的最小概率”,“至多零份 offer 的最小概率”相对的就好求很多,毕竟我们只要求它始终一份 offer 收不到的最小概率,少了很多的限制。

那么设 \(f_{i}\) 为付了 \(i\) 万元还是一份 offer 收不到的最小概率,转移方程如下:

\[f_i = \min_{j=1}^{m}{\{(1-b_j) f_{i-a_j}\}} \]

那么就变成了一个概率背包 DP,大致代码如下:

FOR(i,0,n)f[i]=1.0;//初始化
FOR(i,1,m)DOR(j,n,a[i])tomin(f[j],f[j-a[i]]*(1-b[i]));//转移

(不要在意奇怪的时间复杂度,相信 HDU 的评测机。)

启示

这道题作为概率 DP 的起手题还是非常可以的,它告诉我们一个非常重要的道理就是:不能拘泥于题目给你的信息,要适当的化简或转换,必要时可以套用一些自己知道的数学套路,比如这题中的容斥原理(虽然在这题中用处不明显,但是到了之后的其他概率、期望、计数三类 DP 数学混血中,它可是非常致命的存在)。

HDU - 3076

链接

HDUVJudge

分析

这题状态与转移都显然,但是可能会让人疑惑的点在于:两人会有平局,很多人一开始学的时候就经常不知道怎么处理这种局面,我们来分析一下:

先设状态:\(f_{i,j}\) 表示玩家 1,玩家 2 分别有 \(i\)\(j\) 点生命值时,玩家 1 胜利的概率。

那么边界情况就是:\(\forall i\in[1,HP_1],f_{i,0}\)

转移方程为:\(f_{i,j} = Lose \times f_{i-1,j} + Win \times f_{i,j-1} + Draw \times f_{i,j}\)\(Lose\)\(Win\)\(Draw\) 分别是预处理出来的玩家 1 单次获胜、失败、平局的概率)。

这时候我们就看到了问题所在:等式左右都有 \(f_{i,j}\),这该怎么办?很简单,都说是等式了,那就移项嘛。最终得到转移方程的形式为:

\[\begin{aligned} f_{i,j} & = Lose \times f_{i-1,j} + Win \times f_{i,j-1} + Draw \times f_{i,j} \\ (1 - Draw)f_{i,j} & = Lose \times f_{i-1,j} + Win \times f_{i,j-1} \\ f_{i,j} & = \frac{Lose}{1 - Draw} \times f_{i-1,j} + \frac{Win}{1 - Draw} \times f_{i,j-1} \\ \end{aligned} \]

代码大致如下:

FOR(i,1,6)Draw+=p[0][i]*p[1][i];
FOR(i,1,6)FOR(j,1,i-1)Win+=p[0][i]*p[1][j],Lose+=p[1][i]*p[0][j];
Win/=(1-Draw),Lose/=(1-Draw);//预处理
FOR(i,0,n)f[i][0]=1;//初始化
FOR(i,1,n)FOR(j,1,m)f[i][j]+=f[i-1][j]*Lose+f[i][j-1]*Win;//转移
启示

这道题有一点与其他很多 DP 都不大一样的地方就是:它是逆序的(当然正序也可以),这对于很多初学者来说并不容易理解这样做的原因。其实这样的好处无非就是以下几点:

  1. 正序状态繁杂,不便于求解;
  2. 正序状态不正确,包括情况不完全与情况不合法;
  3. 打代码的人就是喜欢倒序来求。

那么这也侧面折射出一个道理:如果正序不好解题,那么可以考虑倒序,简称“正难则反”。这不只适用于 DP,在很多数据结构题中也是一个非常重要的解题思路,例如并查集。

同时,这题也为我们打开了一种对 DP 转移方程的新理解与运用,这个运用对于接下来的概率和期望 DP 的学习是 十分重要 的。

LightOJ 1265

链接

LightOJVJudge

分析

有了上一题的经验,再加入一些贪心,我们很容易就能解决 DP 状态、决策和转移。

状态:\(f_{i,j}\) 表示还剩 \(i\) 只老虎与 \(j\) 只鹿时人的存活概率。

边界:\(\forall i \in [1,d],f_{0,i}=1\)

转移方程:

\[f_{i,j} = \frac{i \times j \times f_{i,j-1}[j>0]+\frac{i\times(i-1)}{2}f_{i-2,j}[i>1]} {\frac{(i+j+1) \times (i+j)}{2} - \frac{j \times (j-1)}{2} - j} \]

但是我们发现题面中 \(T \le 200\),那 \(O(Tnm)\) 的时间复杂度是肯定过不了的。

于是我们再次思考,发现一个问题:\(f_{i,j}\) 中好像只有 \(i\) 的奇偶性相等的才能互相转移,那么能够转移到边界条件的好像只有 \(i\) 为偶数的状态,而且解题好像与鹿的数量无关。

那么状态就可以化简:\(f_i\) 表示还剩 \(i\) 只老虎人的存活概率。

边界:\(f_0 = 1,f_1 = 0\)

转移方程:

\[f_i = \frac{\frac{i(i-1)}{2}}{\frac{i(i-1)}{2}+i} f_{i-2} \\ \]

那么现在复杂度是 \(O(Tn)\) 的,肯定能过了。

但是如果我把范围上调到 \(1 \le T \le 10^6 ,0 \le t,d \le 10^{18}\),这该怎么办?

看的出来,上面的转移方程可以化简,变成:

\[f_i = \frac{i-1}{i+1} f_{i+2} \\ \]

那么这个递推式就可以转化为通项公式:

\[f_i = \frac{1}{i+1} \\ \]

本题至此结束(代码不放了)。

启示

看完本题的化简过程,我们很容易就可以看出化简对解题的重要性。当然,这个道理在 DP 里肯定是通用的,只不过在与数学结合较多的这类 DP 中要体现的更多而已。

HDU - 1204

链接

HDUVJudge

分析

设出状态和转移:设 \(f_i\) 为玩家 A 有 \(i\) 颗糖时获胜的概率。

转移方程:

\[f_i = p(1-q) f_{i+1} + q(1-p) f_{i-1} + [1 - p(1-q) - q(1-p)] f_i \\ \]

然后呢?移项:

\[[p(1-q) + q(1-p)] f_i - q(1-p) f_{i-1} = p(1-q) f_{i+1} \\ \]

再然后好像就不会了……

这其实是一个 Markov 链,大家可以去了解一下这篇文章,我认为写的很好,易于理解而不失严谨性。其中的 Birth-Death Processes 部分就跟这道题有关,读完之后,你会对这类“随机游走”题有一个更深入的理解。

作为一个基础的随机游走,我们可以尝试使用等比数列化简:

\[f_0 = 0,f_{n+m}=1 \\ q(1-p) (f_i - f_{i-1}) = p(1-q) (f_{i+1} - f_i)\\ (f_{i+1} - f_i) = \frac{q(1-p)}{p(1-q)} (f_i - f_{i-1}) \\ \]

\(K = \frac{q(1-p)}{p(1-q)}\),则:

\[\begin{aligned} f_{n+m} & = \sum_{i=1}^{n+m} (f_i - f_{i-1}) \\ f_{n+m} & = \sum_{i=1}^{n+m} K^{i-1} (f_1 - f_0) \\ f_{n+m} & = (f_1 - f_0) \sum_{i=0}^{n+m-1} K^i \\ f_{n+m} & = (f_1 - f_0) \frac{K^{n+m}-1}{K-1} \\ \end{aligned} \]

\(f_{n}\) 也是同理:

\[f_{n} = (f_1 - f_0)\frac{K^n-1}{K-1} \]

故:

\[f_n = \frac{K^n - 1}{K^{n+m} - 1} f_{n+m},f_{n+m} = 1 \\ f_n = \frac{K^n - 1}{K^{n+m} - 1}\\ \]

再加入一些特判就可以过了(有点多)。

大致代码如下:

P=(p)*(1-q),Q=(1-p)*(q);
if(n==0)cout<<"0.00"<<endl;
else if(m==0)cout<<"1.00"<<endl;
else if(P==Q)Cout(1.0*n/(n+m));
else if(P==1)cout<<"1.00"<<endl;
else if(Q==1)cout<<"0.00"<<endl;
else Cout((1.0-fpow(Q/P,n))/(1.0-fpow(Q/P,n+m)));
启示

我们有时候不能拘泥于状态转移方程的前后顺序,有时候只要在它成立的情况下,前后是可以随意交换的,从而可以推出更多性质。

有些题目需要一点数学功底,我们平时需要多多积累,学以致用。

BZOJ - 3270

链接

BZOJ by HydroOJVJudge

分析

状态依旧是非常容易设:设 \(f_{i,j}\) 表示两人分别出现在 \(i\)\(j\) 的概率。但是迷迷糊糊设出来之后,总感觉不太对劲,有跟上一题一样:它的次数似乎是无限的啊,这怎么能做呢?

其实这依旧是一个 Markov 链,看过上面的推文,就知道满足某些条件的 Markov 链有一个稳态特性(Steady-state behavior)通俗概括就是:

系统的稳态分布是指系统经过一步状态转移后,系统中各个状态的概率分布保持不变。

如果你看不懂推文里的稳态特性条件描述,那你可以看一下另一篇文章,这里面就有一个非常通俗的概括:

首先,Markov 链要能收敛,需要满足以下条件:

  1. 可能的状态数是有限的。
  2. 状态间的转移概率需要固定不变。
  3. 从任意状态能够转变到任意状态。
  4. 不能是简单的循环,例如全是从 \(x\)\(y\) 再从 \(y\)\(x\)

也就是说,这道题的状态是一个收敛Markov 链,它具有稳态特性,那我们就可以合法地列出转移,也就是平衡方程

但是这样的状态不好理解(而且看着就很有问题),我们换一种方法讲述。

显然,这里有无限种游走方案,而我们可以把游走方案的无限化为概率的有限:

\({at}_{i,j}\) 表示两人分别出现在 \(i\)\(j\) 的状态,在所有的游走方案中,\({at}_{i,j}\) 出现的次数都是不确定的,但我们可以用万能的未知数表示出来:我们设 \({times}_{k,i,j}\) 表示在第 \(k\) 种游走方案中 \({at}_{i,j}\) 出现的次数,\(p_k\) 为第 \(k\) 种游走方案出现的概率。

那么设 \(f_{i,j}\) 为两人分别出现在 \(i\)\(j\)概率之和\(f_{i,j} = \sum_{k=1}^{\infin} p_k \times {times}_{k,i,j}\)

其实这条式子我们可以用 \(f_{i,j}\) 的定义转化一下,就变成了这道题的转移方程式:(\(deg_u\) 表示 \(u\) 的出度)

\[\begin{aligned} f_{u,v} & = f_{u,v} \times p_u \times p_v [u \ne v]\\ & + \sum_{(x,u) \in G \land x \ne u} \frac{f_{x,v} \times (1-p_u) \times p_v}{deg_x} \\ & + \sum_{(y,v) \in G \land y \ne v} \frac{f_{u,y} \times p_u \times (1-p_v)}{deg_y} \\ & + \sum_{(x,u) \in G \land (y,v) \in G \land x \ne y} \frac{f_{x,y} \times (1-p_u) \times (1-p_v)}{deg_x \times deg_y} \\ & + [u = S \land v = T] \\ \end{aligned} \]

转移需要我们套用高斯消元(就是求解 \(n\) 元一次方程组),代码大致长这样

启示

在整个理解知识点后,题目做法在眼中就会变得清晰透彻很多。

概率与期望的很多题目都依托于 Markov 链稳态特性,这个知识点一定要吃透。

做一些概率 DP 题目可以依靠一些数学工具来解决或骗分,如:高斯消元、数学归纳法。

还有两个相似的题目:P2973 [USACO10HOL] Driving Out the Piggies GP3232 [HNOI2013] 游走,可以拿来练练手。

参考资料

  1. 概率论中的收敛_百度百科 (baidu.com)
  2. 概率论与统计学5——马尔科夫链(Markov Chain) - 知乎 (zhihu.com)
  3. BZOJ 3270: 博物馆 && 1778: 驱逐猪猡 【概率DP+高斯消元】-CSDN博客
  4. 马尔可夫链 ▏小白都能看懂的马尔可夫链详解-CSDN博客
  5. 齐次Markov链稳态分布的求解_写出状态转移矩阵,并求平稳分布-CSDN博客

期望 DP

期望 DP 相较于概率 DP 不止难了一个档次,所以它才是本文的重点。

性质

在学习期望 DP 之前,这里有几条必须知道或很有用的期望性质:

  1. 期望的加法性质乘法性质

    \[E(\sum X_i) = \sum E(X_i),E(\prod X_i) = \prod E(X_i) \\ \]

    用途:这个是我们用期望来做 DP 的最基本的条件。

  2. 期望的线性性质

    \[E(aX+b) = aE(X) + b \\ \]

    用途:也就是说我们可以把一些不好整体求解的期望拆成很多小部分来求。

  3. 离散型随机变量的定义

    设离散型随机变量 \(X\) 的概率分布为 \(p_i=P\{ X = x_i \}\),若和式

    \[\sum x_i p_i \]

    绝对收敛,则称其值为 \(X\)期望,记作 \(E(X)\)(OI 中的题目大多都是离散型随机变量,故我们只放这一个,其他的连续型可以去百度)。

    用途:通过这个定义,期望可以通过概率来转化求解。

  4. 随机变量函数(复合随机)的数学期望:

    \[E(g(X)) = \sum g(x_i)p_i \\ \]

    用途:也是一条基本性质,可用于辅助 DP。

  5. 奇怪的概率学知识:(相关问题

    对于一个离散型的随机变量 \(X\)\(E(X)\) 的定义为:

    \[E(X) = \sum_{i=1}^n P(X \ge i) \\ \]

    而:\(P(X \ge i) = \sum_{j=i}^n P(X = j)\)

    所以,可以得到:

    \[\begin{aligned} E(X) & = \sum_{i=1}^n P(X \ge i) \\ & = \sum_{i=1}^n \sum_{j=i}^n P(X = j) \\ & = \sum_{j=1}^n \sum_{i=1}^j P(X = j) \\ & = \sum_{i=1}^n i \cdot P(X = i) \\ \end{aligned} \]

    结论:

    \[\sum_{i=1}^n P(X \ge i) = \sum_{i=1}^n i \cdot P(X = i)\\ \]

状态 & 转移

很多期望 DP 的状态转移方程式都有共同点,我们可以学习一些其中的套路。

  1. 状态:设 \(f_{st}\) 为从当前状态 \(st\) 转移到最终状态的期望(步数、花费等)。

    转移:\(f_u = \sum_{(u,v) \in G} p_{(u,v)} \cdot (f_v + w_{(u,v)})\),(\(G\) 代表 DP 状态转移构成的 DAG(有向无环图),下同)。

    应用:在终态明确的 DP 中使用。

  2. 状态:设 \(f_{st}\) 为从最终状态转移到当前状态 \(st\) 的期望(步数、花费等)。

    转移:\(f_v = \sum_{(u,v) \in G} p_{(u,v)} \cdot (f_u + w_{(u,v)})\)

    应用:在初态明确的 DP 中使用。

  3. 状态:设 \(f_{st}\) 为从当前状态转移到下一状态 \(f_{st'}\) 的期望(步数、花费等)。

    求值:\(ans = \sum_i f_i\)

    应用:在链上求随机游走的期望步数等。

  4. 状态:设 \(f_{st}\) 为出现当前状态的概率。

    求值:\(ans = \sum_i f_i \cdot d_i\)

    应用:明确得知或可以获得 \(d_i\) 的情况下。

  5. 状态:把一切条件直接塞入 DP。

    略……

例题

HDU - 3853

链接

HDUVJudge

分析

这题作为期望 DP 的起手题非常不错,状态不难,但初学者很容易被坑(坏笑)。

一个网格会有三个落点,分别是自己、右方、下方,那么如果设状态 \(f_{i,j}\) 为从 \((1,1)\) 走到 \((i,j)\) 的期望,转移方程就较难写。反之,我们如果倒序,设 \(f_{i,j}\) 为从 \((i,j)\) 走到 \((R,C)\) 的期望,那么转移就很清晰明了:

\[f_{R,C} = 0 \\ \begin{aligned} f_{i,j} & = {stay}_{i,j} f_{i,j} + {down}_{i,j} f_{i+1,j} + {right}_{i,j} f_{i,j+1} + 1 \\ (1 - {stay}_{i,j})f_{i,j} & = {down}_{i,j} f_{i+1,j} + {right}_{i,j} f_{i,j+1} + 1 \\ f_{i,j} & = \frac{{down}_{i,j}}{1 - {stay}_{i,j}} f_{i+1,j} + \frac{{right}_{i,j}}{1 - {stay}_{i,j}} f_{i,j+1} + \frac{1}{1 - {stay}_{i,j}} \\ \end{aligned} \]

注意:千万不要移完项再加常数,不然会吃大亏。

代码

Virtual Judge (vjudge.net)

启示

这题用了一个倒推的做法,相关的在概率 DP 中已经讲过了,就不再重复了。

洛谷 - P1850

链接

洛谷VJudge

分析

这道题主要的难点就是 DP 转移的设计,只要有了转移,满分什么的不都是手到擒来(废话……)。

先设 \(g_{i,j}\) 为从 \(i\)\(j\) 的最短距离,用 Floyd 求解一下即可。

\(f_{i,j,0/1}\) 为上完了前 \(i\) 节课,共申请了 \(j\) 次,当前这次是否成功,那么转移方程就没那么难:

\[f_{1,0,0} = 0,f_{1,1,1} = 0 \\ f_{i,j,0} = \min( f_{i-1,j,0} +g_{c_{i-1},c_i}, f_{i-1,j,1} +(1-k_{i-1})g_{c_{i-1},c_i} +k_{i-1}g_{d_{i-1},c_i} )\\ f_{i,j,1} = \min( f_{i-1,j-1,0} +(1-k_{i})g_{c_{i-1},c_i}+k_{i}g_{c_{i-1},d_i},\\ f_{i-1,j-1,1} +k_ik_{i-1}g_{d_{i-1},d_i} +k_i(1-k_{i-1})g_{c_{i-1},d_i} +(1-k_i)k_{i-1}g_{d_{i-1},c_i} +(1-k_i)(1-k_{i-1})g_{c_{i-1},c_i} )\\ \]

代码

Virtual Judge (vjudge.net)

启示

网上有许多博客都说期望 DP 必须倒推,但是其实有很多都是可以正推的,就如这题,做题的时候要养成自己的判断思维。

洛谷 - P6835

链接

洛谷VJudge

分析

这题的部分分很值得练习,但是我们这里主要讲正解。

我们发现似乎直接设 \(f_i\) 为到终态期望好像不太好求,但是我们发现原题只在一条链上,那么我们可以选择设 \(f_i\) 为从 \(i\)\(i+1\) 的期望步数,然后全部累加就是答案。转移式:(\(E_{i \to j}\) 表示从 \(i\) 走到 \(j\) 的期望步数,\(d_i\)\(i\) 的出度)

\[f_i = E_{i \to i+1} , s_i = \sum_{i=1}^{i} f_i \\ \begin{aligned} f_i & = 1 + \frac{1}{d_i+1}\sum_{e(i,j) \in S} (s_i-s_{j-1}) \\ f_i & = 1 + \frac{1}{d_i+1}\sum_{e(i,j) \in S} (s_{i-1}-s_{j-1}) + \frac{d_i}{d_i+1} f_i\\ f_i & = d_i + 1 + \sum_{e(i,j) \in S} (s_{i-1}-s_{j-1})\\ \end{aligned} \]

代码

洛谷

启示

这道题就是我们上面提到的期望的线性性质,同时在做题套路中也有提到。

这题对于没有经验的人来说可能是一道难题,但是一旦做过了就要记住这种套路,毕竟以后也不一定能够再碰到这类练习题了,要抓住机会。

BZOJ - 2720

链接

BZOJ by HydroOJVJudge

分析

BZOJ2720:列队春游(带有部分分) - plus_cat - 博客园 (cnblogs.com)

代码

BZOJ by HydroOJ

启示

其实我对于这道题,最大的一个收获就是上面我讲的奇怪的概率学知识:

\[\sum_{i=1}^n P(X \ge i) = \sum_{i=1}^n i \cdot P(X = i)\\ \]

这个知识点可以在骗分的时候尝试,当然有些题目的正解也是可以用它的。

洛谷 - P4548

链接

洛谷VJudge

分析

这是一个猴子打字问题,题解中的赌博化解释也非常精彩和契合(毕竟本来期望就是为赌博而生的),完美的用一种朴素的、易于理解的并且简单的方法解决了本题。

笔者写不出那么好的题解,也不想被喷抄袭,所以本题就作为一个推荐题放在这里,想看解法的可以自行搜索。

(哦还有这题有超级多倍经验!!!)

代码

Virtual Judge (vjudge.net)

启示

我们对于一个看似复杂的问题,可以通过通俗的转化变成简单的结论,例如联系生活,总之如果发挥天马行空的想象能解决题目,那这也不失为一种非常不错的方法。

CodeForces - 518D

链接

CodeforcesVJudge

分析

如果这题不是求在 \(t\) 秒后,站在自动扶梯上的人的期望值,那么我们其实可以利用期望的线性性质或用终态逆推的方法解决,但它并不是。那该怎么做呢?

如果直接设 \(f_i\)\(i\) 秒后扶梯上的期望人数,似乎不太靠谱……不过这题要是求各个人数的概率的话,倒是十分简单啊,我们在上面的概率 DP 已经有写过类似的题目了。

那我们就可以使用期望(离散型)的定义,转期望为概率。

\(f_{i,j}\) 为在第 \(i\) 秒,站在电梯上的人数为 \(j\) 的概率,答案就是 \(\sum_{i=1}^n f_{t,i} \cdot i\)。转移方程为:

\[f_{i,j} = p \cdot f_{i-1,j-1} + (1-p[j \ne n]) \cdot f_{i-1,j} \]

代码

Codeforces

启示

如果能够把题中的期望转成概率的形式,那么不妨尝试用概率 DP 解决。

LightOJ - 1408

链接

LightOJVJudge

分析

这题是一道公式题,虽略微繁琐,但十分适合练手。

依旧先设状态:\(f_i\)\(g_i\) 分别表示某击球手连续不出局、出局 \(i\) 个球时,会结束的期望球数。

那么列式:

\[f_{k_1} = 0,g_{k_2} = 0 \\ f_{i} = p \cdot g_1 + (1-p) \cdot f_{i+1} + 1,\forall i \in [1,k_1) \\ g_{i} = (1-p) \cdot f_1 + p \cdot g_{i+1} + 1,\forall i \in [1,k_2) \\ \]

我们随意推一下,变成:

\[\begin{aligned} f_{i} & = (1-p) \cdot f_{i+1} + (p \cdot g_1 + 1),\forall i \in [1,k_1) \\ g_{i} & = p \cdot g_{i+1} + [(1-p) \cdot f_1 + 1],\forall i \in [1,k_2) \\ \end{aligned} \]

明显的 \(a_i = k \cdot a_{i-1} +b\),数学归纳法就可以解决。得到:

\[f_1 = (g_1 + \frac{1}{p})[1 - (1-p)^{k_1 - 1}] \\ g_1 = (f_1 + \frac{1}{1-p})(1 - p^{k_2 - 1}) \\ \]

求一下二元一次方程组,即可得到答案:

\[a_1 = 1 - (1-p)^{k_1 - 1},a_2 = 1 - p^{k_2 - 1},b_1 = \frac{1}{p},b_2 = \frac{1}{1-p} \\ f_1 = \frac{a_1 a_2 b_2 + a_1 b_1}{1 - a_1 a_2}, g_1 = \frac{a_2 a_1 b_1 + a_2 b_2}{1 - a_1 a_2} \\ \]

代码

Virtual Judge (vjudge.net)

启示

这应该算是一个简易的 Markov 链,不过它的范围不适合用高斯消元,而且转移式明显可化,那么只能我们手推式子。

平日里自己要多多推一下这种式子,不然到了考场上一慌不会了就完蛋了。

参考资料

  1. 有哪些有趣的概率问题? - 知乎 (zhihu.com)
  2. 题解 P4548 [CTSC2006]歌唱王国 - 洛谷专栏 (luogu.com.cn)。
  3. P4548 的直观理解的通俗严格化 - 洛谷专栏 (luogu.com.cn)

posted @ 2024-08-25 07:38  Add_Catalyst  阅读(251)  评论(0)    收藏  举报