【BZOJ 3561】 DZY Loves Math VI
题目:
给定正整数n,m。求
题解:
水题有益身心健康。(博客园的辣鸡数学公式)
其实到这我想强上伯努利数,然后发现$n^2$的伯努利数,emmmmmm
发现这个式子可以算时间复杂度,emmmmm。积了个分发现时间复杂度很优秀啊(大概也就是$nlog$级别的)。
所以直接算就好了。
P.S.想卡卡常刷一个题榜rank1,emmmm发现自己没这个天赋。
代码:
1 #define Troy 2 3 #include "bits/stdc++.h" 4 5 using namespace std; 6 7 const int mod=1000000007,N=5e5+5; 8 9 inline int powmod(int a,int b){ 10 int ret=1; 11 while(b){ 12 if(b&1) ret=ret*1ll*a%mod; 13 b>>=1; 14 a=a*1ll*a%mod; 15 }return ret; 16 } 17 18 int prim[N],num,mu[N],vis[N],sum[N],ans,f[N]; 19 20 inline int calc(int n,int m,int t){ 21 register int i,j; 22 int ret=0; 23 for (i=1;i<=m;++i){ 24 f[i]=f[i]*1ll*i%mod; 25 vis[i]=mu[i]*(f[i]*1ll*f[i]%mod); 26 vis[i]+=vis[i-1]; 27 vis[i]%=mod; 28 sum[i]=sum[i-1]+f[i]; 29 sum[i]%=mod; 30 } 31 for (i=1;i<=n;i=j+1){ 32 j=min(n/(n/i),m/(m/i)); 33 ret=(ret+(vis[j]-vis[i-1])*1ll*sum[n/i]%mod*sum[m/i])%mod; 34 } 35 return ret; 36 } 37 38 int main(){ 39 int n,m; 40 scanf("%d%d",&n,&m); 41 if(n>m) swap(n,m); 42 register int i,j; 43 for(i=2,mu[1]=1;i<=n;++i){ 44 if(!vis[i]) { 45 mu[i]=-1,prim[++num]=i; 46 }for(j=1;prim[j]*i<=n;++j){ 47 vis[i*prim[j]]=true; 48 if(i%prim[j]==0) { 49 mu[i*prim[j]]=0;break; 50 }mu[i*prim[j]]=-mu[i]; 51 } 52 } 53 for(i=1;i<=m;++i) f[i]=1; 54 for(i=1;i<=n;++i){ 55 ans=(ans+powmod(i,i)*1ll*calc(n/i,m/i,i))%mod; 56 } 57 printf("%d\n",ans); 58 } 59
没有什么不可能。