psy
Description
f(i)=i∗[∑d|n10d∗μ(id)]
f
(
i
)
=
i
∗
[
∑
d
|
n
10
d
∗
μ
(
i
d
)
]
求
∑ni=1f(i)
∑
i
=
1
n
f
(
i
)
Data Constraint
n n <=
Solution
首先显然有
首先设
g(i)
g
(
i
)
=
∑ij=1j∗10j
∑
j
=
1
i
j
∗
10
j
,这个挺容易求,像求等比数列一样裂项求即可,求得
对答案式子分块求,现在只需要求
w(i)=∑ij=1μ(j)∗j
w
(
i
)
=
∑
j
=
1
i
μ
(
j
)
∗
j
考虑到有
w∗ID=[n=1]
w
∗
I
D
=
[
n
=
1
]
,于是可以用杜教筛求解,得
接下来只需预处理出前 n23 n 2 3 的 μ(i)∗i μ ( i ) ∗ i 即可。
Code
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#define fo(i,j,l) for(int i=j;i<=l;++i)
#define fd(i,j,l) for(int i=j;i>=l;--i)
using namespace std;
typedef long long ll;
const ll K=52e5,N=521e4,U=2e5,mo=1e9+7;
int ss[K],oo;
bool bz[N];
int mu[N];
ll qz[N],keep[U],n9,n;
inline ll ksm(ll o,ll t)
{
ll y=1;
for(;t;t>>=1,o=o*o%mo)
if(t&1)y=y*o%mo;
return y;
}
inline ll op(ll t)
{return ((t*ksm(10,t+1)-(ksm(10,t+1)-1)*n9)%mo+mo+1)*n9%mo;}
inline ll ext(ll l,ll r)
{
ll o1=l+r,o2=r-l+1;
if(!(o1&1))o1>>=1;else o2>>=1;
return (o1%mo)*(o2%mo)%mo;
}
ll S(ll p)
{
if(p<=K)return qz[p];
else if(keep[n/p]!=-1)return keep[n/p];
ll l=2,r,lj=0;
while(l<=p){
r=p/(p/l); ll o=p/l;
lj=(lj+ext(l,r)*S(o))%mo;
l=r+1;
}
keep[n/p]=(1-lj+mo)%mo; return keep[n/p];
}
int main()
{
n9=ksm(9,mo-2);
fo(i,2,K){
if(!bz[i])ss[++oo]=i,mu[i]=-1;
fo(j,1,oo)if(ss[j]*i<=K){
bz[ss[j]*i]=true;
mu[ss[j]*i]=-mu[i];
if(i%ss[j]==0){
mu[ss[j]*i]=0;
break;
}
}else break;
}
mu[1]=1;
fo(i,1,U-2)keep[i]=-1;
fo(i,1,K)qz[i]=(qz[i-1]+mu[i]*(i%mo)+mo)%mo;
freopen("psy.in","r",stdin);
freopen("psy.out","w",stdout);
cin>>n;
ll l=1,r,ans=0;
while(l<=n){
r=n/(n/l);
ans=(ans+(S(r)-S(l-1)+mo)*op(n/l))%mo;
l=r+1;
}
cout<<ans;
}