A.Matrix “红旗杯”第十五届东北地区大学生程序设计竞赛

在这里插入图片描述
官方题解
在这里插入图片描述
我只是来复习一下lucas定理然后贴一下代码(普通求组合数也能过)(逃~~)

#include<bits/stdc++.h>
using namespace std;
//#define int long long
typedef long long ll;
const int mod=998244353;
const int N=5050;
ll fact[N*N];
void init(){
	fact[0]=1;
	for(int i=1;i<=N*N;i++) {
		fact[i]=fact[i-1]*i%mod;//初始化阶乘
	}
}
ll fastme(ll base,ll index,ll mod){//快速幂求逆元
	ll res=1;
	while(index){
		if(index&1) res=(ll)res*base%mod;
		index>>=1;
		base=(ll)base*base%mod;
	}
	return res;
}
ll c(ll a,ll b){//求组合数
	return (ll)fact[a]*fastme(fact[a-b],mod-2,mod)%mod*fastme(fact[b],mod-2,mod)%mod;
}
ll lucas(int a,int b){//卢卡斯定理求大数组合数,范围适用1<=b<=a<=1e18
	if(a<mod&&b<mod) return c(a,b);
	return (ll)lucas(a%mod,b%mod)*c(a/mod,b/mod)%mod;
}
int main(){
	init();
	int _;
	cin>>_;
	while(_--){
		int n;
		cin>>n;
		ll ans=0;
		for(int i=1;i<=n;i++){
			ll temp=lucas(n*n-i,n-1)*n%mod;
			ans=(ans+temp)%mod;
		}
		ans=ans*fact[n]%mod*fact[n*n-n]%mod;
		cout<<ans%mod<<endl;
	}	
	return 0;
} 
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值