2694: Lcm
Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 422 Solved: 220
[Submit][Status][Discuss]
Description
对于任意的>1的n gcd(a, b)不是n^2的倍数
也就是说gcd(a, b)没有一个因子的次数>=2
也就是说gcd(a, b)没有一个因子的次数>=2
Input
一个正整数T表示数据组数
接下来T行 每行两个正整数 表示N、M
Output
T行 每行一个整数 表示第i组数据的结果
Sample Input
4
2 4
3 3
6 5
8 3
2 4
3 3
6 5
8 3
Sample Output
24
28
233
178
28
233
178
HINT
HINT
T <= 10000
N, M<=4000000
感谢DZM大爷借我权限号一用2333
然后发现 第三个条件 就是要求gcd没有平方因子,所以写成 *μ^2(gcd(a,b)) 就行了,然后就是一个积性函数题了、、
#include<bits/stdc++.h>
#define ll long long
const int maxn=4000000;
const int ha=1<<30;
using namespace std;
int zs[maxn/5],t=0,T,n,m;
int low[maxn+5],f[maxn+5];
bool v[maxn+5];
inline int add(int x,int y){
x+=y;
return x>=ha?x-ha:x;
}
inline void init(){
low[1]=f[1]=1;
for(int i=2;i<=maxn;i++){
if(!v[i]) zs[++t]=i,low[i]=i,f[i]=1-i;
for(int j=1,u;j<=t&&(u=zs[j]*i)<=maxn;j++){
v[u]=1;
if(!(i%zs[j])){
low[u]=low[i]*zs[j];
if(!v[low[i]]) f[u]=f[i/low[i]]*-low[i];
else f[u]=0;
break;
}
low[u]=zs[j];
f[u]=f[i]*f[zs[j]];
}
}
for(int i=1;i<=maxn;i++) f[i]=add(add(f[i],ha)*(ll)i%ha,f[i-1]);
}
inline int solve(){
int an=0;
if(n>m) swap(n,m);
for(int i=1,nx,ny,j;i<=n;i=j+1){
nx=n/i,ny=m/i,j=min(n/nx,m/ny);
an=add(an,((nx+1)*(ll)nx>>1)%ha*(ll)(((ny+1)*(ll)ny>>1)%ha)%ha*(ll)add(f[j],ha-f[i-1])%ha);
}
return an;
}
int main(){
init();
scanf("%d",&T);
while(T--){
scanf("%d%d",&n,&m);
printf("%d\n",solve());
}
return 0;
}