社区讨论

WA了7个点,求大佬改错。

P3704[SDOI2017] 数字表格参与者 4已保存回复 4

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
4 条
当前快照
1 份
快照标识符
@mi7pemtz
此快照首次捕获于
2025/11/21 01:27
4 个月前
此快照最后确认于
2025/11/21 01:27
4 个月前
查看原帖
CPP
#include<iostream>
#include<cstdio>
#include<cstdlib>
#define re register
#define LL long long
#define N 1000005
using namespace std;
const LL Mod=1e9+7; const int lim=1e6;
LL T,n,m,f[N],g[N],mul[N],inv_mul[N],p_cnt,mu[N],p[100005]; bool vis[N];
LL power(LL x,LL P){
	LL ans=1,c=x;
	while(P){
		if(P&1) ans=(ans*c%Mod+Mod)%Mod;
		P>>=1; c=(c*c%Mod+Mod)%Mod;
	}
	return ans;
}
void get_f(){
	f[1]=f[2]=1;
	for(re int i=3;i<=lim;++i) f[i]=(f[i-1]+f[i-2])%Mod;
	for(re int i=1;i<=lim;++i) g[i]=power(f[i],Mod-2);
}
void get_mu(){
	mu[1]=1;
	for(re int i=2;i<=lim;++i){
		if(!vis[i]) p[++p_cnt]=i,mu[i]=-1;
		for(re int j=1;j<=p_cnt;++j){
			if(i*p[j]>lim) break; vis[i*p[j]]=1;
			if(i%p[j]==0) break; mu[i*p[j]]=-mu[i];
		}
	}
}
void get_mul(){
	for(re int i=0;i<=lim;++i) mul[i]=1;
	for(re int i=1;i<=lim;++i)
	for(re int j=1;i*j<=lim;++j){
		if(mu[j]==1) mul[i*j]=(mul[i*j]*f[i]%Mod+Mod)%Mod;
		else if(mu[j]==-1) mul[i*j]=(mul[i*j]*g[i]%Mod+Mod)%Mod;
	}
	for(re int i=1;i<=lim;++i) mul[i]=(mul[i]*mul[i-1]%Mod+Mod)%Mod;
	for(re int i=0;i<=lim;++i) inv_mul[i]=power(mul[i],Mod-2);
}
int main(){
	scanf("%lld",&T); get_f(); get_mu(); get_mul();
	for(re int i=1;i<=T;++i){
		scanf("%lld%lld",&n,&m); LL ans=1;
		if(n>m){ LL t=n; n=m; m=t; }
		for(re LL l=1,r;l<=n;l=r+1){
			r=min(n/(n/l),m/(m/l));
			ans=(ans*power((mul[r]*inv_mul[l-1]%Mod+Mod)%Mod,((n/l)*(m/l)%Mod+Mod)%Mod)%Mod+Mod)%Mod;
		}
		printf("%lld\n",ans);
	}
	return 0;
}

回复

4 条回复,欢迎继续交流。

正在加载回复...