[洛谷 P3768] 简单的数学题 (莫比乌斯反演 狄利克雷卷积 杜教筛)

题意:

∑ i = 1 n ∑ j = 1 n i j gcd ⁡ ( i , j ) \sum_{i=1}^{n}\sum_{j=1}^{n}ij\gcd(i,j) i=1nj=1nijgcd(i,j)

p p p 取模, n ≤ 1 0 10 , 5 × 1 0 8 ≤ p ≤ 1.1 × 1 0 9 n \le10^{10}, 5 ×10^8\le p \le1.1 ×10^{9} n1010,5×108p1.1×109

分析:

∑ i = 1 n ∑ j = 1 n i j gcd ⁡ ( i , j ) \sum_{i=1}^{n}\sum_{j=1}^{n}ij\gcd(i,j) i=1nj=1nijgcd(i,j)

枚举 gcd ⁡ ( i , j ) \gcd(i,j) gcd(i,j)

∑ d = 1 n d ∑ i = 1 n ∑ j = 1 n i j [ gcd ⁡ ( i , j ) = d ] \sum_{d=1} ^{n} d \sum_{i=1}^{n}\sum_{j=1}^{n}ij[\gcd(i,j)=d] d=1ndi=1nj=1nij[gcd(i,j)=d]

利用 gcd ⁡ \gcd gcd 的性质

∑ d = 1 n d ∑ i = 1 n ∑ j = 1 n i j [ gcd ⁡ ( i d , j d ) = 1 ] \sum_{d=1} ^{n} d \sum_{i=1}^{n}\sum_{j=1}^{n}ij[\gcd(\frac{i}{d},\frac{j}{d})=1] d=1ndi=1nj=1nij[gcd(di,dj)=1]

让式子除 d 2 d^2 d2 再乘 d 2 d^2 d2

∑ d = 1 n d 3 ∑ i = 1 n ∑ j = 1 n i d ⋅ j d [ gcd ⁡ ( i d , j d ) = 1 ] \sum_{d=1} ^{n} d^3 \sum_{i=1}^{n}\sum_{j=1}^{n} \frac{i}{d} \cdot \frac{j}{d}[\gcd(\frac{i}{d},\frac{j}{d})=1] d=1nd3i=1nj=1ndidj[gcd(di,dj)=1]

换一下上界

∑ d = 1 n d 3 ∑ i = 1 ⌊ n d ⌋ ∑ j = 1 ⌊ n d ⌋ i j [ gcd ⁡ ( i , j ) = 1 ] \sum_{d=1} ^{n} d^3 \sum_{i=1}^{\lfloor \frac{n}{d} \rfloor}\sum_{j=1}^{\lfloor \frac{n}{d} \rfloor} i j[\gcd(i,j)=1] d=1nd3i=1dnj=1dnij[gcd(i,j)=1]

莫比乌斯反演

∑ d = 1 n d 3 ∑ i = 1 ⌊ n d ⌋ ∑ j = 1 ⌊ n d ⌋ i j ∑ k ∣ gcd ⁡ ( i , j ) μ ( k ) \sum_{d=1} ^{n} d^3 \sum_{i=1}^{\lfloor \frac{n}{d} \rfloor}\sum_{j=1}^{\lfloor \frac{n}{d} \rfloor} i j \sum_{k \mid \gcd(i,j)} \mu(k) d=1nd3i=1dnj=1dnijkgcd(i,j)μ(k)

交换求和次序

∑ d = 1 n d 3 ∑ k = 1 ⌊ n d ⌋ μ ( k ) ∑ i = 1 ⌊ n d k ⌋ i k ∑ j = 1 ⌊ n d k ⌋ j k \sum_{d=1} ^{n} d^3 \sum_{k=1} ^{\lfloor \frac{n}{d} \rfloor} \mu(k) \sum_{i=1}^{\lfloor \frac{n}{dk} \rfloor} ik\sum_{j=1}^{\lfloor \frac{n}{dk} \rfloor} jk d=1nd3k=1dnμ(k)i=1dknikj=1dknjk

化简后半部分

∑ d = 1 n d 3 ∑ k = 1 ⌊ n d ⌋ k 2 μ ( k ) ( ∑ i = 1 ⌊ n d k ⌋ i ) 2 \sum_{d=1} ^{n} d^3 \sum_{k=1} ^{\lfloor \frac{n}{d} \rfloor} k^2 \mu(k) (\sum_{i=1} ^{\lfloor \frac{n}{dk} \rfloor}i)^2 d=1nd3k=1dnk2μ(k)(i=1dkni)2

T = d k T=dk T=dk

∑ T = 1 n T 2 ∑ d ∣ T d μ ( T d ) ( ∑ i = 1 ⌊ n T ⌋ i ) 2 \sum_{T=1} ^{n} T^2 \sum_{d \mid T} d\mu(\frac{T}{d}) (\sum_{i=1} ^{\lfloor \frac{n}{T} \rfloor}i)^2 T=1nT2dTdμ(dT)(i=1Tni)2

因为 μ ∗ I d = φ \mu * Id=\varphi μId=φ,替换 ∑ d ∣ T d μ ( T d ) \sum \limits_{d \mid T} d\mu(\frac{T}{d}) dTdμ(dT)

∑ T = 1 n T 2 φ ( T ) ( ∑ i = 1 ⌊ n T ⌋ i ) 2 \sum_{T=1} ^{n} T^2 \varphi(T) (\sum_{i=1} ^{\lfloor \frac{n}{T} \rfloor}i)^2 T=1nT2φ(T)(i=1Tni)2

根据 ( n 2 + n 2 ) 2 = 1 3 + 2 3 + ⋯ + n 3 (\dfrac{n^2 +n}{2})^2=1^3+2^3+\cdots+n^3 (2n2+n)2=13+23++n3

∑ T = 1 n T 2 φ ( T ) ∑ i = 1 ⌊ n T ⌋ i 3 \sum_{T=1} ^{n} T^2 \varphi(T) \sum_{i=1} ^{\lfloor \frac{n}{T} \rfloor}i^3 T=1nT2φ(T)i=1Tni3

f ( x ) = x 2 φ ( x ) f(x)= x^2\varphi(x) f(x)=x2φ(x) 套用杜教筛, S ( n ) S(n) S(n) ∑ i = 1 n f ( i ) \sum \limits_{i=1}^{n} f(i) i=1nf(i)

g ( 1 ) S ( n ) = ∑ i = 1 n h ( i ) − ∑ i = 1 n g ( i ) S ( ⌊ n i ⌋ ) g(1)S(n)=\sum_{i=1} ^{n}h(i)-\sum_{i=1}^{n}g(i)S(\lfloor \frac{n}{i} \rfloor) g(1)S(n)=i=1nh(i)i=1ng(i)S(⌊in⌋)

那么 h = f ∗ g h=f *g h=fg,也就是 h ( n ) = ∑ d ∣ n f ( d ) g ( n d ) h(n)=\sum \limits _{d \mid n}f(d)g(\dfrac{n}{d}) h(n)=dnf(d)g(dn),带入 f ( n ) f(n) f(n)

h ( n ) = ∑ d ∣ n d 2 φ ( d ) g ( n d ) h(n)=\sum_{d \mid n} d^2\varphi(d)g(\frac{n}{d}) h(n)=dnd2φ(d)g(dn)

考虑把 d 2 d^2 d2 消去,所以设 g ( x ) = x 2 g(x)=x^2 g(x)=x2,故

h ( n ) = n 2 ∑ d ∣ n φ ( d ) h(n)=n^2\sum_{d \mid n}\varphi(d) h(n)=n2dnφ(d)

根据 φ ∗ I = I d \varphi *I=Id φI=Id

h ( n ) = n 3 h(n)=n^3 h(n)=n3

那么 f ( x ) f(x) f(x) 的前缀和就是

S ( n ) = ( n 2 + n 2 ) 2 − ∑ i = 2 n i 2 S ( ⌊ n i ⌋ ) S(n)=(\frac{n^2+n}{2})^2-\sum_{i=2} ^{n}i^2S(\lfloor \frac{n}{i} \rfloor) S(n)=(2n2+n)2i=2ni2S(⌊in⌋)

代码:

#include <bits/stdc++.h>
#define int long long
using namespace std;
const int N = 5e6 + 5;
int mod, n, euler[N], primes[N], cnt, sum[N], inv, res;
bool st[N];
unordered_map<int, int> mp;
int qmi(int a, int b) {
    int res = 1;
    while (b) {
        if (b & 1) res = res * a % mod;
        a = a * a % mod;
        b >>= 1;
    }
    return res;
}
void get_eulers(int n) {
    euler[1] = 1;
    for (int i = 2; i <= n; i ++) {
        if (!st[i]) {
            primes[cnt ++] = i;
            euler[i] = i - 1;
        }
        for (int j = 0; primes[j] <= n / i; j ++) {
            int t = primes[j] * i;
            st[t] = 1;
            if (i % primes[j] == 0) {
                euler[t] = primes[j] * euler[i];
                break;
            }
            euler[t] = (primes[j] - 1) * euler[i];
        }
    }
    for (int i = 1; i <= n; i ++) sum[i] = (sum[i - 1] + i * i % mod * euler[i] % mod) % mod;
}
int s2(int n) {
    n %= mod;
    return n * (n + 1) % mod * (2 * n + 1) % mod * inv % mod;
}
int s3(int n) {
    n %= mod;
    return (n * (n + 1) / 2) % mod * ((n * (n + 1) / 2) % mod) % mod;
}
int Sum(int n) {
    if (n < N) return sum[n];
    if (mp[n]) return mp[n];
    int res = s3(n);
    for (int l = 2, r; l <= n; l = r + 1) {
        r = n / (n / l);
        res -= (s2(r) - s2(l - 1) + mod) % mod * Sum(n / l) % mod;
        res = (res + mod) % mod;
    }
    return mp[n] = res;
}
signed main() {
    cin >> mod >> n;
    get_eulers(N - 1);
    inv = qmi(6, mod - 2);
    for (int l = 1, r; l <= n; l = r + 1) {
        r = n / (n / l);
        res += (Sum(r) - Sum(l - 1) + mod) % mod * s3(n / l) % mod;
        res = (res % mod + mod) % mod;
    }
    cout << res << endl;
}
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值