标签:ble 有一个 org ref const 怎么 个数 cout 因子
luogu
求\[\sum_{i=l}^ri-\phi(i)\]
一个朴素的想法是枚举l~r,根号求\(\phi\),显然这样是\((r-l)\sqrt r\),时间无法承受
考虑怎么优化求\(\phi\)的时间,
我们知道对于一个数x,超过\(\sqrt x\)的质因子最多只有一个
我们考虑对[l,r]的数开vector记录质因子
我们可以线筛求出\(\sqrt r\)以内的质数,枚举它们的倍数放到相应的[l,r]的vector中
再枚举l~r求\(\phi\)
这样时间和空间都是\((r-l)logr\)
#define ll long long
#include<bits/stdc++.h>
using namespace std;
const int _=1000005;
int mx,cnt,p[100000];
ll l,r,ans;
bool vis[_];
vector<int>v[_];
int main(){
cin>>l>>r;mx=sqrt(r);
for(int i=2;i<=mx;i++){
if(!vis[i])p[++cnt]=i;
for(int j=1;j<=cnt&&p[j]*i<=mx;j++){
vis[p[j]*i]=1;if(i%p[j]==0)break;
}
}
for(int i=1;i<=cnt;i++){
ll k=ceil(1.0*l/p[i])*p[i];
while(k<=r)v[k-l].push_back(p[i]),k+=p[i];
}
for(int i=0;i<=r-l;i++){
ll x=i+l,phi=i+l;
for(int j=0,sz=v[i].size();j<sz;j++){
int k=v[i][j];
phi/=k;phi*=k-1;
while(x%k==0)x/=k;
}
if(x>1)phi/=x,phi*=x-1;
ans=(ans+i+l-phi)%666623333;
}
cout<<ans<<endl;
return 0;
}
标签:ble 有一个 org ref const 怎么 个数 cout 因子
原文地址:https://www.cnblogs.com/sdzwyq/p/9931810.html