http://www.lydsy.com/JudgeOnline/problem.php?id=2820
推一波式子
$$sum_{isprime(p)}sum_{a=1}^nsum_{b=1}^mgcd(a,b)==p$$
$$sum_{isprime(p)}sum_{a=1}^{left lfloor frac{n}{p} ight floor}sum_{b=1}^{left lfloor frac{m}{p} ight floor}gcd(a,b)==1$$
$$sum_{isprime(p)}sum_{a=1}^{left lfloor frac{n}{p} ight floor}sum_{b=1}^{left lfloor frac{m}{p} ight floor}sum_{d|gcd(a,b)}mu(d)$$
$$sum_{isprime(p)}sum_{a=1}^{left lfloor frac{n}{p} ight floor}sum_{b=1}^{left lfloor frac{m}{p} ight floor}sum_{d|a land d|b}mu(d)$$
$$sum_{isprime(p)}sum_{d=1}^{left lfloor frac{n}{p} ight floor}mu(d){leftlfloorfrac{n}{pd} ight floor}{leftlfloor frac{m}{pd} ight floor}$$
将pd设为k
$$sum_{k=1}^{n}sum_{isprime(p) land p|k}mu(frac{k}{p}){left lfloor frac{n}{k}
ight
floor}{left lfloor frac{m}{k}
ight
floor}$$
$$sum_{k=1}^{n}F(k){left lfloorfrac{n}{k}
ight
floor}{left lfloor frac{m}{k}
ight
floor}$$
就可以线性筛处理F了
#include<cstdio> #include<algorithm> #define maxn 10000007 #define LL long long LL x,y; int n,prime[maxn],miu[maxn],cnt,f[maxn],sum[maxn]; bool v[maxn]; void get_pre() { miu[1]=1; for(int i=2;i<=maxn-7;i++) { if(!v[i]) { v[i]=true;prime[++cnt]=i; miu[i]=-1;f[i]=1; } for(int j=1;j<=cnt;j++) { if(i*prime[j]>maxn-7) break; v[i*prime[j]]=true; if(i%prime[j]==0) { miu[i*prime[j]]=0; f[i*prime[j]]=miu[i]; break; } miu[i*prime[j]]=-miu[i]; f[i*prime[j]]=miu[i]-f[i]; } } for(int i=1;i<=maxn-7;i++) sum[i]=sum[i-1]+f[i]; } int main() { get_pre(); scanf("%d",&n); while(n--) { scanf("%lld%lld",&x,&y); LL k=std::min(x,y),j,ans=0; for(LL i=1;i<=k;i=j+1) { j=std::min(x/(x/i),y/(y/i)); ans+=(x/i)*(y/i)*(sum[j]-sum[i-1]); } printf("%lld ",ans); } return 0; }