bzoj4916 神犇和蒟蒻(杜教筛)

题意:

给定n,要求计算:
∑ i = 1 n μ ( i 2 ) \sum_{i=1}^nμ(i^2) i=1nμ(i2)
∑ i = 1 n φ ( i 2 ) \sum_{i=1}^nφ(i^2) i=1nφ(i2)
答案对1e9+7取模

数据范围:n<=1e9

解法:

第一问的答案一定是1,因为只有12没有平方质因子,其他都有,
根据莫比乌斯函数定义,有平方质因子的数的莫比乌斯函数值为0

那么剩下的就是第二问了:
欧拉函数: φ ( n ) = n p 1 p 2 . . . p m ( p 1 − 1 ) ( p 2 − 1 ) . . ( p m − 1 ) φ(n)=\frac {n}{p_{1}p_{2}...p_{m}}(p_{1}-1)(p_{2}-1)..(p_{m}-1) φ(n)=p1p2...pmn(p11)(p21)..(pm1)
因为n2的质因子在n中已经出现过了,那么: φ ( n 2 ) = n 2 p 1 p 2 . . . p m ( p 1 − 1 ) ( p 2 − 1 ) . . ( p m − 1 ) φ(n^2)=\frac {n^2}{p_{1}p_{2}...p_{m}}(p_{1}-1)(p_{2}-1)..(p_{m}-1) φ(n2)=p1p2...pmn2(p11)(p21)..(pm1)
可以把分子的一个n提出来,那么: φ ( n 2 ) φ(n^2) φ(n2)= n ∗ φ ( n ) n*φ(n) nφ(n)
问题变为计算 ∑ i = 1 n i ∗ φ ( i ) \sum_{i=1}^ni*φ(i) i=1niφ(i)

推导:
∑ i = 1 n i ∗ φ ( i ) \sum_{i=1}^ni*φ(i) i=1niφ(i)
令 f = i ∗ φ ( i ) , 选 择 g = i d ( i ) = i 令f=i*φ(i),选择g=id(i)=i f=iφ(i),g=id(i)=i
那 么 ( f ∗ g ) ( n ) = ∑ d ∣ n f ( d ) ∗ g ( n d ) 那么(f*g)(n)=\sum_{d|n}f(d)*g(\frac nd) (fg)(n)=dnf(d)g(dn)
= ∑ d ∣ n d ∗ φ ( d ) ∗ n d =\sum_{d|n}d*φ(d)*\frac nd =dndφ(d)dn
= n ∗ ∑ d ∣ n φ ( d ) =n*\sum_{d|n}φ(d) =ndnφ(d)
= n 2 =n^2 =n2
最后一步用了欧拉函数的性质 ∑ d ∣ n φ ( d ) = n \sum_{d|n}φ(d)=n dnφ(d)=n

综上: ( f ∗ g ) ( i ) = i 2 (f*g)(i)=i^2 (fg)(i)=i2

杜教筛递推式: g ( 1 ) S ( n ) = ∑ i = 1 n ( f ∗ g ) ( i ) − ∑ i = 2 n g ( i ) S ( ⌊ n i ⌋ ) g(1)S(n)=\sum_{i=1}^n(f*g)(i)-\sum_{i=2}^ng(i)S(\lfloor \frac ni \rfloor) g(1)S(n)=i=1n(fg)(i)i=2ng(i)S(in)
代入得: S ( n ) = ∑ i = 1 n i 2 − ∑ i = 2 n i ∗ S ( ⌊ n i ⌋ ) = n ∗ ( n + 1 ) ∗ ( 2 n + 1 ) 6 − ∑ i = 2 n i ∗ S ( ⌊ n i ⌋ ) S(n)=\sum_{i=1}^ni^2-\sum_{i=2}^ni*S(\lfloor \frac ni \rfloor)=\frac {n*(n+1)*(2n+1)}{6}-\sum_{i=2}^ni*S(\lfloor \frac ni \rfloor) S(n)=i=1ni2i=2niS(in)=6n(n+1)(2n+1)i=2niS(in)

code:
#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int maxm=1e6+5;
const int mod=1e9+7;
const int inv6=166666668;
ll phi[maxm];
ll notprime[maxm];
ll prime[maxm],cnt;
ll sum_p[maxm];
void init(){
    phi[1]=1;
    for(int i=2;i<maxm;i++){
        if(!notprime[i]){
            prime[cnt++]=i;
            phi[i]=i-1;
        }
        for(int j=0;j<cnt;j++){
            if(prime[j]*i>=maxm)break;
            notprime[prime[j]*i]=1;
            phi[prime[j]*i]=phi[i]*(i%prime[j]?prime[j]-1:prime[j]);
            if(i%prime[j]==0)break;
        }
    }
    for(int i=1;i<maxm;i++){
        sum_p[i]=(sum_p[i-1]+phi[i]*i%mod)%mod;
    }
}
map<ll,ll>mp_p;
ll cal(ll x){
    return x*(x+1)/2;
}
ll S_p(ll x){
    if(x<maxm)return sum_p[x];
    if(mp_p[x])return mp_p[x];
    ll ans=x*(x+1)%mod*(2*x+1)%mod*inv6%mod;
    for(ll i=2,j;i<=x;i=j+1){
        j=x/(x/i);
        ll temp=(cal(j)-cal(i-1))%mod;
        ans-=temp*S_p(x/i)%mod;
        ans%=mod;
    }
    ans=(ans%mod+mod)%mod;
    return mp_p[x]=ans;
}
signed main(){
    init();
    ll n;scanf("%lld",&n);
    printf("1\n%lld",S_p(n));
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值