Live2D

Solution -「CF 1392H」ZS Shuffles Cards

Description

  Link.

  打乱的 n 张编号 1n 的数字排和 m 张鬼牌。随机抽牌,若抽到数字,将数字加入集合 S;否则,还原牌堆(但不清空 S)。若 S=[1,n] 且抽到鬼牌时结束抽牌。求期望抽牌次数。

  n,m2×106

Solution

  称从初始牌堆开始抽牌一直到抽到鬼牌为一轮操作,发现结束时必然抽了若干个完整的轮且不能中途终止。所以“抽完一轮”和“结束抽牌”两事件独立,分别记二者的随机变量为 ξ1ξ2,则答案为 E(ξ1ξ2)=E(ξ1)E(ξ2)

  E(ξ1) 显然等于一轮抽到数字牌的期望张数 +1。 而由期望线性性,它也等于 n×p+1,其中 p 表示抽到某一张牌的概率,有:

p=1m+1

  一种直观的解释方法是,把每张数字牌和 m 张鬼牌绑为一组,每次拿出这样一组牌,再从中随机选出一张作为抽到的牌,其它牌丢掉,不难证明这和原操作等价。显然拿出某一张数字牌所在的组时,有 p=1m+1 的概率真正拿到这张数字牌,不然就永远拿不到了。于是,我们求到了:

E(ξ1)=nm+1+1


  求 E(ξ2),令 f(i) 表示已有 |S|=ni,到结束时的期望轮数。方程有:

f(i)=mm+i(f(i)+1)+im+if(i1)

  特别留意上式,总牌数 m+i 是因为其他 ni 张数字牌没有任何意义,可以忽略;前一项抽到鬼牌,轮数才要 +1;后一项抽到有用数字牌,但是这一轮并没有结束,所以不用 +1

  整理一下:

f(i)=f(i1)+mi

  对于边界 f(1),即 m+1 张里挑出一张的期望,显然有 f(1)=m+1。代一代求出 f(n)

f(n)=1+mi=1n1i

  综上,答案为:

E(ξ1ξ2)=E(ξ1)E(ξ2)=(nm+1+1)f(n)=(nm+1+1)(1+mi=1n1i)

  计算即可。复杂度 O(n+logm)

Code

/* Clearink */

#include <cstdio>

const int MOD = 998244353, MAXN = 2e6;
int n, m, inv[MAXN + 5];

inline int qkpow ( int a, int b, const int p = MOD ) {
	int ret = 1;
	for ( ; b; a = 1ll * a * a % p, b >>= 1 ) ret = 1ll * ret * ( b & 1 ? a : 1 ) % p;
	return ret;
}

int main () {
	scanf ( "%d %d", &n, &m );
	int turn = ( n + m + 1ll ) * qkpow ( m + 1, MOD - 2 ) % MOD, times = 1;
	for ( int i = 1; i <= n; ++ i ) {
		inv[i] = i ^ 1 ? 1ll * inv[MOD % i] * ( MOD - MOD / i ) % MOD : 1;
		times = ( times + 1ll * m * inv[i] ) % MOD;
	}
	printf ( "%d\n", int ( 1ll * turn * times % MOD ) );
	return 0;
}
posted @   Rainybunny  阅读(95)  评论(0编辑  收藏  举报
编辑推荐:
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现
点击右上角即可分享
微信分享提示