HDU-7314 2023“钉耙编程”杭电多校赛(4)Data Generation

文章讲述了如何使用矩阵和递推关系求解一个编程竞赛题目,涉及给定n和m计算特定算法中a变量期望值的问题,利用矩阵快速幂优化求解,时间复杂度为O(logm)。

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

HDU-7314 2023“钉耙编程”杭电多校赛(4)Data Generation

题目大意

给定 n n n m m m,求下面的算法中 a n s ans ans的期望值模 998244353 998244353 998244353后的结果。

在这里插入图片描述
T T T组数据。

1 ≤ T ≤ 1 0 5 , 1 ≤ n ≤ 1 0 18 , 0 ≤ m ≤ 1 0 18 1\leq T\leq 10^5,1\leq n\leq 10^{18},0\leq m\leq 10^{18} 1T105,1n1018,0m1018

数据保证 n n n不是 998244353 998244353 998244353的倍数。


题解

显然对于每个 1 ≤ i ≤ n 1\leq i\leq n 1in m m m次交换后 a i ≠ i a_i\neq i ai=i的概率是相同的,那题意即求 [ a 0 ≠ 0 ] [a_0\neq 0] [a0=0]的期望值 × n \times n ×n,我们只需要求 [ a 0 ≠ 0 ] [a_0\neq 0] [a0=0]的期望值。

f i f_i fi表示在第 i i i次交换后 a 0 = 0 a_0=0 a0=0的概率, g i g_i gi表示在第 i i i次交换后 a 0 ≠ 0 a_0\neq 0 a0=0的概率。则递推式如下:

f i = f i − 1 × 1 + ( n − 1 ) 2 n 2 + g i − 1 × 2 n 2 f_i=f_{i-1}\times \dfrac{1+(n-1)^2}{n^2}+g_{i-1}\times \dfrac{2}{n^2} fi=fi1×n21+(n1)2+gi1×n22

g i = f i − 1 × [ 1 − 1 + ( n − 1 ) 2 n 2 ] + g i − 1 × ( 1 − 2 n 2 ) g_i=f_{i-1}\times [1-\dfrac{1+(n-1)^2}{n^2}]+g_{i-1}\times (1-\dfrac{2}{n^2}) gi=fi1×[1n21+(n1)2]+gi1×(1n22)

用矩阵优化:

[ f i g i ] = [ 1 + ( n − 1 ) 2 n 2 2 n 2 1 − 1 + ( n − 1 ) 2 n 2 1 − 2 n 2 ] × [ f i − 1 g i − 1 ] \left[ \begin{matrix} f_i \\ g_i \end{matrix} \right]= \left[ \begin{matrix} \frac{1+(n-1)^2}{n^2} & \frac{2}{n^2} \\ 1-\frac{1+(n-1)^2}{n^2} & 1-\frac{2}{n^2} \end{matrix} \right]\times \left[ \begin{matrix} f_{i-1} \\ g_{i-1} \end{matrix} \right] [figi]=[n21+(n1)21n21+(n1)2n221n22]×[fi1gi1]

那么

[ f m g m ] = [ 1 + ( n − 1 ) 2 n 2 2 n 2 1 − 1 + ( n − 1 ) 2 n 2 1 − 2 n 2 ] m × [ f 0 g 0 ] \left[ \begin{matrix} f_m \\ g_m \end{matrix} \right]= \left[ \begin{matrix} \frac{1+(n-1)^2}{n^2} & \frac{2}{n^2} \\ 1-\frac{1+(n-1)^2}{n^2} & 1-\frac{2}{n^2} \end{matrix} \right]^m\times \left[ \begin{matrix} f_0 \\ g_0 \end{matrix} \right] [fmgm]=[n21+(n1)21n21+(n1)2n221n22]m×[f0g0]

因为 f 0 = 1 f_0=1 f0=1,答案为 n × g m n\times g_m n×gm,所以下列矩阵的第二行第一列的数乘 n n n即为答案。

[ 1 + ( n − 1 ) 2 n 2 2 n 2 1 − 1 + ( n − 1 ) 2 n 2 1 − 2 n 2 ] m \left[ \begin{matrix} \frac{1+(n-1)^2}{n^2} & \frac{2}{n^2} \\ 1-\frac{1+(n-1)^2}{n^2} & 1-\frac{2}{n^2} \end{matrix} \right]^m [n21+(n1)21n21+(n1)2n221n22]m

这个矩阵可以用矩阵快速幂来求。

时间复杂度为 O ( ∑ log ⁡ m ) O(\sum \log m) O(logm)

code

#include<bits/stdc++.h>
using namespace std;
const long long mod=998244353;
int T;
long long n,m,ny,p1,p2,p3,p4;
struct matrix{
	long long a[2][2];
	matrix operator*(const matrix ax)const{
		matrix cx;
		for(int i=0;i<2;i++){
			for(int j=0;j<2;j++){
				cx.a[i][j]=0;
				for(int k=0;k<2;k++){
					cx.a[i][j]=(cx.a[i][j]+a[i][k]*ax.a[k][j])%mod;
				}
			}
		}
		return cx;
	}
}w;
long long in(){
	long long t=0,fl=1;
	char ch=getchar();
	while(ch<'0'||ch>'9') ch=getchar();
	while(ch>='0'&&ch<='9'){
		t=t*10+ch-'0';ch=getchar();
	}
	return t*fl;
}
long long mi(long long t,long long v){
	if(!v) return 1;
	long long re=mi(t,v/2);
	re=re*re%mod;
	if(v&1) re=re*t%mod;
	return re;
}
matrix dd(matrix t,long long v){
	matrix re;
	re.a[0][1]=re.a[1][0]=0;
	re.a[0][0]=re.a[1][1]=1;
	while(v){
		if(v&1) re=re*t;
		v>>=1;t=t*t;
	}
	return re;
}
int main()
{
	T=in();
	while(T--){
		n=in();m=in();n%=mod;
		ny=mi(n,mod-2);
		p1=(1+(n-1)*(n-1))%mod*ny%mod*ny%mod;
		p2=2*ny*ny%mod;
		p3=(1-p1+mod)%mod;
		p4=(1-p2+mod)%mod;
		w.a[0][0]=p1;w.a[0][1]=p2;
		w.a[1][0]=p3;w.a[1][1]=p4;
		w=dd(w,m);
		printf("%lld\n",w.a[1][0]*n%mod);
	}
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值