【莫比乌斯函数】【SPOJ 4491】PGCD

来源:互联网 发布:迪杰斯特拉算法应用 编辑:程序博客网 时间:2024/04/29 19:13

http://www.spoj.com/problems/PGCD/


这篇讲得很好了

http://www.cnblogs.com/kuangbin/p/3378531.html



亲测手写min和改了几个int快了5s


//#define _TEST _TEST#include <cstdio>#include <cstring>#include <cstdlib>#include <iostream>#include <cmath>#include <algorithm>using namespace std;/************************************************Code By willinglive    Blog:http://willinglive.cf************************************************/#define rep(i,l,r) for(int i=l,___t=(r);i<=___t;i++)#define per(i,r,l) for(int i=r,___t=(l);i>=___t;i--)#define MS(arr,x) memset(arr,x,sizeof(arr))#define LL long long#define INE(i,u,e) for(int i=head[u];~i;i=e[i].next)inline const 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 k*r;}/////////////////////////////////////////////////const int N=10000000;int n,m;int mu[10000010],prim[2000010],cnt;bool flag[10000010];int g[10000010];int s[10000010];/////////////////////////////////////////////////LL min(LL a,LL b){return a<b?a:b;}void get_mu(){mu[1]=1;rep(i,2,N){if(!flag[i]) prim[++cnt]=i,mu[i]=-1,g[i]=1;for(int j=1;j<=cnt && i*prim[j]<=N;j++){flag[i*prim[j]]=1;if(i%prim[j]==0){mu[i*prim[j]]=0;g[i*prim[j]]=mu[i];break;}else{mu[i*prim[j]]=-mu[i];g[i*prim[j]]=-g[i]+mu[i];}}}rep(i,1,N) s[i]=s[i-1]+g[i];}/////////////////////////////////////////////////void solve(){    get_mu();for(int T=read();T--;)    {    LL ans=0;    n=read(); m=read();    if(n>m) swap(n,m);    int r;    for(int i=1;i<=n;i=r+1)    {    r=min(n/(n/i),m/(m/i));    ans+=(LL)(s[r]-s[i-1])*(n/i)*(m/i);    }    printf("%lld\n",ans);    }}/////////////////////////////////////////////////int main(){    freopen("std.in","r",stdin); freopen("std.out","w",stdout);    solve();    return 0;}


0 0
原创粉丝点击