LightOJ

这里有个小技巧   对于任意一个数n

与他 gcd 为k  的数 的和为  欧拉函数(n/k)*n*k/2

然后这题就可以在0(nlog)解决

不然你也可以用反演直接搞....

#include<bits/stdc++.h>
#define MAXN 3000000
using namespace std;

int p[MAXN/5],tot,euler[MAXN+5],T,n,cishu;
unsigned long long sum[MAXN+5],fa[MAXN+5];
bitset<MAXN+5>vis;

void init(){
    euler[0]=euler[1]=1;
    for(int i=2;i<=MAXN;i++){
        if(vis[i]==0)euler[i]=i-1,tot++,p[tot]=i;
        for(int j=1;j<=tot&&i*p[j]<=MAXN;j++){
            vis[i*p[j]]=1;
            if(i%p[j]==0){euler[i*p[j]]=euler[i]*p[j];break;}
            euler[i*p[j]]=euler[i]*(p[j]-1);
        }
    }
    sum[0] = sum[1] = 0;
    for(int i=2;i<=MAXN;i++){
        for(int j=i;j<=MAXN;j+=i){
            fa[j] += (euler[i]*j*i/2);
        }
        sum[i] = sum[i-1]+fa[i];
    }
    for(int i=1;i<=10;i++)cout<<fa[i]<<"  "<<euler[i]<<"   "<<i<<endl;
}

int main(){
    init();
    cin>>T;
    while(T--){
        cishu++;cout<<"Case "<<cishu<<": ";
        cin>>n;
        cout<<sum[n]<<endl;
    }
}
原文地址:https://www.cnblogs.com/shatianming/p/12359269.html