P3704 [SDOI2017]数字表格
#include<iostream> #include<cstdio> #include<cstring> #define LL long long #define maxn 1000009 #define N maxn+10 #define M 1000000007 using namespace std; int n,m; int q; LL ksm(LL a,LL p){ LL ans=1; for(;p;p>>=1,a=a*a%M){ if(p&1)ans=ans*a%M; } return ans; } inline LL inv(LL a){ return ksm(a,M-2); } int vis[N]; int mu[N]; int prime[N],cnt; LL f[N]; LL g[N]; LL invg[N]; int shake(){ mu[1]=1;vis[1]=1; for(int i=2;i<=maxn;++i){ if(!vis[i]){ prime[++cnt]=i; mu[i]=-1; } for(int j=1;j<=cnt&&i*prime[j]<=maxn;++j){ vis[i*prime[j]]=1; if(i%prime[j]==0){ mu[i*prime[j]]=0; break; } mu[i*prime[j]]=-mu[i]; } } f[1]=f[2]=1; for(int i=3;i<=maxn;++i)f[i]=(f[i-1]+f[i-2])%M; for(int i=0;i<=maxn;++i)g[i]=1; for(int d=1;d<=maxn;++d){ LL inverse=inv(f[d]); for(int k=1;k*d<=maxn;++k){ if(mu[k]==1){ g[k*d]=g[k*d]*f[d]%M; } if(mu[k]==-1){ g[k*d]=g[k*d]*inverse%M; } } } for(int i=2;i<=maxn;++i)g[i]=g[i]*g[i-1]%M; for(int i=0;i<=maxn;++i)invg[i]=inv(g[i]); } inline int read(){ int r=0,k=1; char c=getchar(); for(;c<'0'||c>'9';c=getchar())if(c=='-')k=-1; for(;c>='0'&&c<='9';c=getchar())r=r*10+c-'0'; return r*k; } int main(){ //freopen("product.in","r",stdin); //freopen("product.out","w",stdout); shake(); q=read(); while(q--){ n=read();m=read(); if(n>m)swap(n,m); int last;LL ans=1; for(int i=1;i<=n;i=last+1){ last=min(n/(n/i),m/(m/i)); ans=ans*ksm(g[last]*invg[i-1]%M,(LL)(n/i)*(m/i))%M; } printf("%d\n",ans); } return 0; }
致歉:笔者已经意识到这是一篇几乎没有价值的文章,给您的阅读带来不好的体验,并且干扰了您的搜索环境,非常抱歉!