快乐地打牢基础(14)——莫比乌斯反演

数论千万条,反演第一条。反演不会做,队友两行泪。

一、什么是莫比乌斯反演?

  • g ( n ) = ∑ d ∣ n f ( d ) ⟺ f ( n ) = ∑ d ∣ n μ ( d ) g ( n d ) . . . . . . . . . . . . . ( 1 ) {g(n) = \displaystyle\sum_{d|n}f(d)\Longleftrightarrow f(n) = \displaystyle\sum_{d|n}\mu(d)g(\frac{n}{d})}.............(1) g(n)=dnf(d)f(n)=dnμ(d)g(dn).............(1)
  • g ( n ) = ∑ n ∣ d f ( d ) ⟺ f ( n ) = ∑ n ∣ d μ ( d n ) g ( d ) . . . . . . . . . . . . . . ( 2 ) {g(n) = \displaystyle\sum_{n|d}f(d)\Longleftrightarrow f(n) = \displaystyle\sum_{n|d}\mu(\frac{d}{n})g(d)}..............(2) g(n)=ndf(d)f(n)=ndμ(nd)g(d)..............(2)

很多时候函数 f f f很难求,但是函数 g g g可以比较容易的求出来,所有我们通过求出 g g g来求出 f f f,这个由 g g g求出 f f f的过程就是反演。

二、前置知识


1.莫比乌斯函数

μ ( n ) = { 1 ,            n = 1 ( − 1 ) k ,    n = P 1 P 2 . . . P k 0 ,            o t h e r \mu(n) =\begin{cases} 1,\ \ \ \ \ \ \ \ \ \ n=1\\ (-1)^k,\ \ n = P_1P_2...P_k\\0,\ \ \ \ \ \ \ \ \ \ other\end{cases} μ(n)=1,          n=1(1)k,  n=P1P2...Pk0,          other
其中 P 1 P 2 . . . P k P_1P_2...P_k P1P2...Pk为质数。

莫比乌斯函数推导

线性筛求莫比乌斯函数:

int prime_tot = 0;
bool prime_tag[N];
int prime[N],mu[N];

void get_prime(){
    mu[1] = 1;//n = 1时,莫比乌斯函数mu[1] = 1,
    for(int i = 2; i < N; i++){
        if(!prime_tag[i]) prime[prime_tot++] = i,mu[i] = -1;//如果i是一个质数,那么其莫比乌斯函数一定是-1
        for(int j = 0; j < prime_tot && i * prime[j] < N; j++){
            prime_tag[i * prime[j]] = true;
            if(i % prime[j] == 0){
                mu[i * prime[j]] = 0;//可以知道此处prime[j] | i,
                					//那么i * prime[j]里就有一个prime[j]的平方存在
                break;
            }else
                mu[i * prime[j]] = -mu[i];//i * prime[j]为k个质数的乘积,如果k是奇数mu[i]就是-1,
                						//是偶数mu[i]为1
        }
    }
}

2.狄利克雷卷积

狄利克雷卷积是一个对函数的运算。

狄利克雷卷积:
对于两个函数 f , g f,g f,g,它们的狄利克雷卷积是

( f ∗ g ) ( n ) = ∑ d ∣ n f ( d ) g ( n d ) (f*g)(n) = \displaystyle\sum_{d|n}f(d)g(\frac{n}{d}) (fg)(n)=dnf(d)g(dn)

积性函数:
两个数 a , b a,b a,b互质,对于函数 f f f,如果 f ( a b ) = f ( a ) f ( b ) f(ab)=f(a)f(b) f(ab)=f(a)f(b),那么函数 f f f就是一个积性函数。

完全积性函数:
任意两个数 a , b a,b a,b,都有 f ( a b ) = f ( a ) f ( b ) f(ab)=f(a)f(b) f(ab)=f(a)f(b)

常见的积性函数

  • 欧拉函数 φ ( n ) \varphi(n) φ(n)
  • 莫比乌斯函数 μ ( n ) \mu(n) μ(n)
  • 单位函数 I d ( n ) = n Id(n) = n Id(n)=n
  • 不变函数 1 ( n ) = 1 1(n) = 1 1(n)=1,不变的函数,所有值都是 1 1 1
  • 幂函数 i d k ( k ) = n k idk(k) = n^k idk(k)=nk
  • 因子个数函数 d ( n ) , d = 1 ( n ) ∗ 1 ( n ) d(n),d = 1(n)*1(n) d(n),d=1(n)1(n),n的正因子数目
  • 因子和函数 σ ( n ) , σ = 1 ( n ) ∗ I d , n \sigma(n),\sigma = 1(n)*Id,n σ(n),σ=1(n)Idn的所有正因子之和
  • 因子函数 σ k ( n ) σk(n) σk(n),n的所有正因子的k次幂之和
  • 狄利克雷卷积单位元 ε = [ n = = 1 ] \varepsilon = [n==1] ε=[n==1]
  • 逆元:对于每一个 f ( 1 ) = 0̸ f(1)=\not0 f(1)=0的函数 f f f,都有 f ∗ g = ε f∗g=\varepsilon fg=ε

如何求一个函数的逆元:
首先我们定义两个函数 f , g f,g f,g
g ( n ) = 1 f ( 1 ) ( [ n = = 1 ] − ∑ i ∣ n , i ≠ 1 f ( i ) g ( n i ) ) g(n)=\frac{1}{f(1)}\left([n==1]-\sum_{i|n,i\neq 1}f(i)g(\frac{n}{i})\right) g(n)=f(1)1[n==1]in,i=1f(i)g(in)
这样的话,他们的狄利克雷卷积 f ∗ g f*g fg 就是:
∑ i ∣ n f ( i ) g ( n i )                                  = f ( 1 ) g ( n ) + ∑ i ∣ n , i ≠ 1 f ( i ) g ( n i )                                                                                          = f ( 1 ) ∗ 1 f ( 1 ) ( [ n = = 1 ] − ∑ i ∣ n , i ≠ 1 f ( i ) g ( n i ) ) + ∑ i ∣ n , i ≠ 1 f ( i ) g ( n i ) = [ n = = 1 ] \sum_{i|n}f(i)g(\frac{n}{i})\\\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ =f(1)g(n)+\sum_{i|n,i\neq1}f(i)g(\frac{n}{i})\\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ =f(1)*\frac{1}{f(1)}\left([n==1]-\sum_{i|n,i\neq 1}f(i)g(\frac{n}{i})\right)+ \sum_{i|n,i\neq1}f(i)g(\frac{n}{i})\\=[n==1] inf(i)g(in)                                =f(1)g(n)+in,i=1f(i)g(in)                                                                                        =f(1)f(1)1[n==1]in,i=1f(i)g(in)+in,i=1f(i)g(in)=[n==1]
此处证明推导均来自:铃悬dalao的博客

一些关于莫比乌斯函数和狄利克雷卷积单位元的性质

1.不变常数 1 1 1 和莫比乌斯函数 μ \mu μ 互为逆元。

用上述求逆元的方法直接套,令 g ( n ) = 1 ( n ) , f ( n ) = μ ( n ) g(n) = 1(n),f(n) = \mu(n) g(n)=1(n),f(n)=μ(n)

2.两个积性函数的狄利克雷卷积是积性函数。

3.积性函数的逆是积性函数。

2和3具体详细的证明还是参考铃悬dalao的博客https://www.luogu.org/blog/lx-2003/mobius-inversion

3.整除分块

看一个题目:求 ∑ k = 1 n ⌊ n k ⌋ \displaystyle\sum^{n}_{k= 1}\lfloor\frac{n}{k}\rfloor k=1nkn的值。
可能会想到暴力,直接遍历一遍,但当 n n n很大的时候,时间是使dalao们不满意的。
所以有了整除分块的想法。
n = 25 n = 25 n=25 来举例:
首先可以发现, ⌊   n     k   ⌋ \lfloor \frac{\ n\ }{\ k\ }\rfloor  k  n  只有 2 n 2\sqrt{n} 2n 种,那我们按照 ⌊   n     k   ⌋ \lfloor \frac{\ n\ }{\ k\ }\rfloor  k  n  的结果分类的:
快乐地打牢基础(14)——莫比乌斯反演_第1张图片

int ans = 0;
for(int l = 1 , r; l <= n; l = r + 1){
	r = n / (n / l);
	ans += (r - l + 1)(n / l);
}

这样一来,整除通过这种分块的思想就把时间复杂度降到了 O ( 2 n ) O(2\sqrt{n}) O(2n )

三、莫比乌斯反演的证明


  • g ( n ) = ∑ d ∣ n f ( d ) ⟺ f ( n ) = ∑ d ∣ n μ ( d ) g ( n d ) . . . . . . . . . . . . . ( 1 ) {g(n) = \displaystyle\sum_{d|n}f(d)\Longleftrightarrow f(n) = \displaystyle\sum_{d|n}\mu(d)g(\frac{n}{d})}.............(1) g(n)=dnf(d)f(n)=dnμ(d)g(dn).............(1)
  • g ( n ) = ∑ n ∣ d f ( d ) ⟺ f ( n ) = ∑ n ∣ d μ ( d n ) g ( d ) . . . . . . . . . . . . . . ( 2 ) {g(n) = \displaystyle\sum_{n|d}f(d)\Longleftrightarrow f(n) = \displaystyle\sum_{n|d}\mu(\frac{d}{n})g(d)}..............(2) g(n)=ndf(d)f(n)=ndμ(nd)g(d)..............(2)

首先证明 ( 1 ) (1) (1),这很好证明( 1 1 1代表不变函数):
g = f ∗ 1 , f = μ ∗ g = μ ∗ 1 ∗ f = f g = f*1,f = \mu*g=\mu *1*f=f g=f1,f=μg=μ1f=f
然后证明 ( 2 ) (2) (2)
k = d n k = \frac{d}{n} k=nd,则:
∑ n ∣ d μ ( d n ) g ( d ) = ∑ k μ ( k ) g ( n k ) = ∑ k μ ( k ) ∑ ( n k ) ∣ t f ( t ) \sum_{n|d}\mu(\frac{d}{n})g(d)=\sum_{k}\mu(k)g(nk)=\sum_{k}\mu(k)\sum_{(nk)|t}f(t) ndμ(nd)g(d)=kμ(k)g(nk)=kμ(k)(nk)tf(t)
∑ t f ( t ) ∑ ( n k ) ∣ t μ ( k ) = ∑ t f ( t ) ε ( t n ) = f ( n ) {\displaystyle \sum_{t}f(t)\sum_{(nk)|t}\mu(k)=\sum_{t}f(t)\varepsilon(\frac{t}{n})=f(n)} tf(t)(nk)tμ(k)=tf(t)ε(nt)=f(n)

四、一点点题目


注:所有例题中 g c d ( x , y ) gcd(x,y) gcd(x,y)都为 x , y x,y x,y的最大公约数。

【例1】luogu P2522 [HAOI2011]Problem b
题意

对于给定的 T T T个询问,每次求友多少个数对 ( x , y ) (x,y) (x,y)满足 a ≤ x ≤ b , c ≤ y ≤ d a\leq x\leq b,c\leq y\leq d axb,cyd,且 g c d ( x , y ) = k gcd(x,y) = k gcd(x,y)=k

思路
首先可以将问题使用容斥原理转化一下:

定义 s o l v e ( b , d ) solve(b,d) solve(b,d)为数对 ( x , y ) (x,y) (x,y)是满足 1 ≤ x ≤ b , 1 ≤ y ≤ d 1\leq x\leq b,1\leq y\leq d 1xb,1yd,且 g c d ( x , y ) = k gcd(x,y)=k gcd(x,y)=k的个数。

根据容斥原理:

a n s = s o l v e ( b , d ) − s o l v e ( a − 1 , d ) − s o l v e ( b , c − 1 ) + s o l v e ( a − 1 , c − 1 ) ans = solve(b,d) - solve(a-1,d) - solve(b,c-1) + solve(a-1,c-1) ans=solve(b,d)solve(a1,d)solve(b,c1)+solve(a1,c1)

这样就可以利用一种类似于前缀和的方法求出来答案。

问题就转化为求出 1 ≤ x ≤ ⌊ b k ⌋ , 1 ≤ y ≤ ⌊ d k ⌋ 1\leq x\leq \lfloor\frac{b}{k}\rfloor,1\leq y\leq \lfloor\frac{d}{k}\rfloor 1xkb,1ykd,且 g c d ( x , y ) = 1 gcd(x,y)=1 gcd(x,y)=1的数对个数。

下面利用莫比乌斯反演,来解题:

首先设
f ( i ) = ∑ x = 1 n ∑ y = 1 m [ g c d ( x , y ) = = i ] f(i) = \displaystyle\sum_{x=1}^{n}\sum_{y=1}^{m}[gcd(x,y) == i] f(i)=x=1ny=1m[gcd(x,y)==i]

g ( i ) = ∑ x = 1 n ∑ y = 1 m [ i   ∣   g c d ( x , y ) ] = ⌊ n i ⌋ ⌊ m i ⌋ g(i) = \displaystyle\sum_{x=1}^{n}\sum_{y = 1}^{m}[i\ |\ gcd(x,y)]=\lfloor\frac{n}{i}\rfloor\lfloor\frac{m}{i}\rfloor g(i)=x=1ny=1m[i  gcd(x,y)]=inim

f ( i ) = ∑ i ∣ q μ ( q i ) g ( q ) = ∑ i ∣ q μ ( q i ) ⌊ n q ⌋ ⌊ m q ⌋ f(i) = \displaystyle\sum_{i|q }\mu(\frac{q}{i})g(q)= \displaystyle\sum_{i|q }\mu(\frac{q}{i})\lfloor\frac{n}{q}\rfloor\lfloor\frac{m}{q}\rfloor f(i)=iqμ(iq)g(q)=iqμ(iq)qnqm

通过之前推导出的红字,可以知道现在需要的就是求出 f ( 1 ) f(1) f(1),将 i = 1 , n = ⌊ b k ⌋ , m = ⌊ d k ⌋ i = 1,n = \lfloor\frac{b}{k}\rfloor,m= \lfloor\frac{d}{k}\rfloor i=1n=kbm=kd代入,可以得到:

f ( 1 ) = ∑ 1 ∣ q μ ( q 1 ) g ( q ) = ∑ 1 ∣ q μ ( q 1 ) ⌊ b q k ⌋ ⌊ d q k ⌋ f(1) = \displaystyle\sum_{1|q }\mu(\frac{q}{1})g(q)= \displaystyle\sum_{1|q }\mu(\frac{q}{1})\lfloor\frac{b}{qk}\rfloor\lfloor\frac{d}{qk}\rfloor f(1)=1qμ(1q)g(q)=1qμ(1q)qkbqkd

然后使用分块处理可得到答案。

//莫比乌斯反演例题
#include
#include
#include
#include
#include
#define ll long long
using namespace std;

const int N = 5e4 + 10;
bool prime_tag[N] = {0};
int prime[N],mu[N],prime_tot = 0;
ll sum[N] = {0};
int cas,a,b,c,d,k;

void get_mu(){
    mu[1] = 1;
    for(int i = 2; i < N; i++){
        if(!prime_tag[i]){
            prime[prime_tot++] = i;
            mu[i] = -1;
        }
        for(int j = 0; j < prime_tot && i * prime[j] < N; j++){
            prime_tag[i * prime[j]] = true;
            if(i % prime[j] == 0){
                 mu[i * prime[j]] = 0;
                 break;
            }else{
                mu[i * prime[j]] = -mu[i];
            }
        }
    }
    sum[0] = 0;
    for(int i = 1; i < N; i++)
        sum[i] = sum[i - 1] + mu[i];
}
ll solve(ll b ,ll d){
    b = b / k;
    d = d / k;
    ll res = 0;
    int t = min(b,d);
    for(int l = 1,r; l <= t; l = r + 1){
        r = min((ll)b / (b / l),(ll)d / (d / l));
        res += (sum[r] - sum[l - 1]) * (b / l ) * (d / l);
    }
    return res;
}
int main(){
    get_mu();
    //read(cas);
    scanf("%d",&cas);
    while(cas--){
        //read(a);read(b);read(c);read(d);read(k);
        scanf("%d %d %d %d %d",&a,&b,&c,&d,&k);
        //printf("%d %d %d %d %d\n",a,b,c,d,k);
        printf("%lld\n",solve(b,d) - solve(a-1,d) - solve(b,c-1) + solve(a-1,c-1));
    }
    return 0;
}

【例2】luogu P2257 YY的GCD
题意
给定 N , M N,M NM,求 1 ≤ x ≤ N , 1 ≤ y ≤ M 1\leq x \leq N,1\leq y \leq M 1xN,1yM g c d ( x , y ) gcd(x,y) gcd(x,y)为质数的 ( x , y ) (x,y) (x,y)有多少对?
思路
和上一题很像,区别在于要确保 g c d ( x , y ) = = k , k gcd(x,y) == k,k gcd(x,y)==k,k是一个质数。
f ( x ) = ∑ x ∈ p r i m e ∑ x   ∣   d μ ( d x ) g ( d ) f(x) = \displaystyle\sum_{x\in prime}\sum_{x\ | \ d}\mu(\frac{d}{x})g(d) f(x)=xprimex  dμ(xd)g(d)

          = ∑ d = 1 m i n ( n , m ) ⌊ n d ⌋ ⌊ m d ⌋ ∑ x ∈ p r i m e , x   ∣   d μ ( d x ) \ \ \ \ \ \ \ \ \ =\displaystyle\sum_{d = 1}^{min(n,m)}\lfloor\frac{n}{d}\rfloor\lfloor\frac{m}{d}\rfloor\sum_{x\in prime ,x\ |\ d}\mu(\frac{d}{x})          =d=1min(n,m)dndmxprime,x  dμ(xd)

这里我们可以令:
s u m [ d ] = ∑ x ∈ p r i m e , x   ∣   d μ ( d x ) sum[d] = \displaystyle\sum_{x\in prime ,x\ |\ d}\mu(\frac{d}{x}) sum[d]=xprime,x  dμ(xd)

这样一来:
f ( x ) = ∑ x ∈ p r i m e ∑ x   ∣   d μ ( d x ) g ( d ) f(x) = \displaystyle\sum_{x\in prime}\sum_{x\ | \ d}\mu(\frac{d}{x})g(d) f(x)=xprimex  dμ(xd)g(d)

          = ∑ d = 1 m i n ( n , m ) ⌊ n d ⌋ ⌊ m d ⌋ s u m [ d ] \ \ \ \ \ \ \ \ \ =\displaystyle\sum_{d = 1}^{min(n,m)}\lfloor\frac{n}{d}\rfloor\lfloor\frac{m}{d}\rfloor sum[d]          =d=1min(n,m)dndmsum[d]

预处理代码:

    sum[0] = 0;
    for(int i = 0 ; i < prime_tot; i++){
        for(int j  = 1; prime[i] * j < N; j++){
            sum[prime[i] * j] += mu[j];
        }
    }
    for(int i = 1 ; i < N; i++)
        sum[i] += sum[i-1] + sum[i];

提前预处理这个 s u m ( d ) sum(d) sum(d),再求一个前缀和就可以很好的放在分块中解决

#include 
#include 
#include 
#include 
#include 
#define ll long long
using namespace std;

const int N = 1e7 + 7;
int prime[N],prime_tot = 0,mu[N];
ll sum[N] = {0};
bool prime_tag[N] = {0};
int cas,n,m;

void get_mu(){
    mu[1] = 1;
    for(int i = 2; i < N; i++){
        if(!prime_tag[i]){
            prime[prime_tot++] = i;
            mu[i] = -1;
        }
        for(int j = 0 ; j < prime_tot && i * prime[j] < N; j++){
            prime_tag[i * prime[j]] = true;
            if(i % prime[j] == 0){
                mu[i * prime[j]] = 0;
                break;
            }
                mu[i * prime[j]] = -mu[i];
        }
    }
    sum[0] = 0;
    for(int i = 0 ; i < prime_tot; i++){
        for(int j  = 1; prime[i] * j < N; j++){
            sum[prime[i] * j] += mu[j];
        }
    }
    for(int i = 1 ; i < N; i++)
        sum[i] += sum[i-1] + sum[i];
}
ll solve(){
    ll res = 0,res1 = 0;
    for(int l = 1,r; l <= n; l = r + 1){
        r = min(n / (n / l),m / (m / l));
        res += (ll) (sum[r] - sum[l - 1]) * (n / l) * (m / l);
    }

    return res / 2;
}
int main(){
    get_mu();
    scanf("%d",&cas);
    while(cas--){
        scanf("%d %d",&n,&m);
        if(n > m) swap(n,m);
        printf("%lld\n",solve());

    }
    return 0;
}

【例3】luogu P4449 于神之怒加强版
题意
给定 n , m , k n,m,k n,m,k,计算 ∑ i = 1 n ∑ j = 1 m g c d ( i , j ) k   m o d ( 1 0 9 + 7 ) \displaystyle\sum_{i = 1}^{n}\sum_{j = 1}^{m}gcd(i,j)^k\ mod(10^9+7) i=1nj=1mgcd(i,j)k mod(109+7)的值。
思路
枚举最大公因数 d d d,并计算最大公因数为 d d d 的数对个数 ∑ i = 1 n ∑ j = 1 m [ g c d ( i , j ) = = d ] \displaystyle\sum_{i = 1}^{n}\sum_{j = 1}^{m}[gcd(i,j)==d] i=1nj=1m[gcd(i,j)==d]的值
那么答案就是 ∑ d m i n ( n , m ) 最 大 公 因 数 为 d 的 数 对 个 数 × d k \displaystyle\sum_d^{min(n,m)}最大公因数为 d的数对个数\times d^k dmin(n,m)d×dk
我们使用莫比乌斯反演:
f ( u ) = ∑ i = 1 n ∑ j = 1 m [ g c d ( i , j ) = = u ] . . . . . . . . ( 1 ) g ( u ) = ∑ i = 1 n ∑ j = 1 m [ u ∣ g c d ( i , j ) ] = ⌊ n u ⌋ ⌊ m u ⌋ . . . . . . . . ( 2 ) f(u) = \displaystyle\sum_{i = 1}^{n}\sum_{j = 1}^{m}[gcd(i,j)==u]........(1) \\g(u) = \displaystyle\sum_{i = 1}^{n}\sum_{j = 1}^{m}[u|gcd(i,j)] = \lfloor\frac{n}{u}\rfloor\lfloor\frac{m}{u}\rfloor........(2) f(u)=i=1nj=1m[gcd(i,j)==u]........(1)g(u)=i=1nj=1m[ugcd(i,j)]=unum........(2)

f ( u ) = ∑ u ∣ p μ ( p u ) g ( p ) f(u) = \displaystyle\sum_{u|p}\mu(\frac{p}{u})g(p) f(u)=upμ(up)g(p)
由于
∑ i = 1 n ∑ j = 1 m [ g c d ( i , j ) = = d ] \displaystyle\sum_{i = 1}^{n}\sum_{j = 1}^{m}[gcd(i,j)==d] i=1nj=1m[gcd(i,j)==d] ∑ i = 1 n d ∑ j = 1 m d [ g c d ( i , j ) = = 1 ] \displaystyle\sum_{i = 1}^{\frac{n}{d}}\sum_{j = 1}^{\frac{m}{d}}[gcd(i,j)==1] i=1dnj=1dm[gcd(i,j)==1]是等价的

( 1 ) ( 2 ) (1)(2) (1)(2)中的 n = ⌊ n d ⌋ , m = ⌊ n d ⌋ , u = 1 n = \lfloor\frac{n}{d}\rfloor,m = \lfloor\frac{n}{d}\rfloor,u = 1 n=dn,m=dn,u=1

f ( 1 ) = ∑ p μ ( p 1 ) ⌊ n d × p ⌋ ⌊ m d × p ⌋ f(1) = \displaystyle\sum_{p}\mu(\frac{p}{1})\lfloor\frac{n}{d\times p}\rfloor\lfloor\frac{m}{d\times p}\rfloor f(1)=pμ(1p)d×pnd×pm(注意此时 ⌊ n d × p ⌋ \lfloor\frac{n}{d\times p}\rfloor d×pn中的 ⌊ n d ⌋ \lfloor\frac{n}{d}\rfloor dn是常量,是不变换的)

a n s = ∑ d d k ∑ p μ ( p ) ⌊ n d p ⌋ ⌊ m d p ⌋ ans = \displaystyle\sum_dd^k\displaystyle\sum_{p}\mu(p)\lfloor\frac{n}{ dp}\rfloor\lfloor\frac{m}{ dp}\rfloor ans=ddkpμ(p)dpndpm
为了使形式更加明显一些,设 Q = d p Q = dp Q=dp

a n s = ∑ Q ⌊ n Q ⌋ ⌊ m Q ⌋ ∑ d   ∣   Q d k μ ( Q d ) ans = \displaystyle\sum_Q\displaystyle\lfloor\frac{n}{ Q}\rfloor\lfloor\frac{m}{ Q}\rfloor \sum_{d\ |\ Q}d^k\mu(\frac{Q}{d}) ans=QQnQmd  Qdkμ(dQ)

到这里我们设 F ( Q ) = ∑ d   ∣   Q d k μ ( Q d ) F(Q) = \displaystyle \sum_{d\ |\ Q}d^k\mu(\frac{Q}{d}) F(Q)=d  Qdkμ(dQ),可以很(bu)容易发现 F ( Q ) F(Q) F(Q)是一个狄利克雷卷积的形式。
顺便再来复习狄利克雷卷积的定义:

( f ∗ g ) ( n ) = ∑ d ∣ n f ( d ) g ( n d ) (f*g)(n) = \displaystyle\sum_{d|n}f(d)g(\frac{n}{d}) (fg)(n)=dnf(d)g(dn)

那么 F = i d k ∗ u F = idk*u F=idku

我们的答案就变成了:

a n s = ∑ Q ⌊ n Q ⌋ ⌊ m Q ⌋ F ( Q ) ans = \displaystyle\sum_Q\displaystyle\lfloor\frac{n}{ Q}\rfloor\lfloor\frac{m}{ Q}\rfloor F(Q) ans=QQnQmF(Q)

前一部分直接使用分块可以很好的求出, F ( Q ) F(Q) F(Q)则需要使用线性筛来预处理,并求出前缀和。

根据狄利克雷卷积的性质,因为 i d k idk idk μ \mu μ 都是积性函数所以 F F F也是积性函数,那么 F F F就可以像 φ \varphi φ一样利用 F ( a × b ) = F ( a ) × F ( b ) F(a\times b) = F(a)\times F(b) F(a×b)=F(a)×F(b)求出。

对于 F ( Q ) = ∑ d   ∣   Q d k μ ( Q d ) F(Q) = \displaystyle \sum_{d\ |\ Q}d^k\mu(\frac{Q}{d}) F(Q)=d  Qdkμ(dQ),将Q按唯一分解定理分解:
Q = p 1 c 1 p 2 c 2 . . . p m c m Q = p_1^{c1}p_2^{c2}...p_m^{cm} Q=p1c1p2c2...pmcm

F ( Q ) = ∏ i = 1 m F ( p i c i ) . . . . . . . . ( 1 ) F(Q) = \displaystyle\prod_{i =1}^m F(p_i^{ci})........(1) F(Q)=i=1mF(pici)........(1)

同时,对于 F ( p i c i ) F(p_i^{ci}) F(pici),因为莫比乌斯函数的性质, μ ( p r i m e ) = − 1 , μ ( 1 ) = 1 \mu(prime)=-1,\mu(1)=1 μ(prime)=1,μ(1)=1,所以只有在 d = p i c i − 1 d = p_i^{ci-1} d=pici1 d = p i c i d = p_i^{ci} d=pici 时对 ∑ d   ∣   p i c i d k μ ( p i c i d ) \displaystyle \sum_{d\ |\ p_i^{ci}}d^k\mu(\frac{p_i^{ci}}{d}) d  picidkμ(dpici)有贡献。所以, ( 1 ) (1) (1)可以转化为:

F ( Q ) F(Q) F(Q)
= ∏ i = 1 m ( p i k × ( c i − 1 ) × μ ( p i )   +   p i k × c i × μ ( 1 ) ) \displaystyle=\prod_{i=1}^{m}(p_i^{k\times (ci-1)}\times \mu(p_i)\ +\ p_i^{k\times c_i}\times \mu(1)) =i=1m(pik×(ci1)×μ(pi) + pik×ci×μ(1))

= ∏ i = 1 m p i k × ( c i − 1 ) × ( p i k − 1 ) \displaystyle =\prod_{i=1}^{m}p_i^{k\times (ci-1)}\times(p_i^{k}-1) =i=1mpik×(ci1)×(pik1)

p r i m e [ j ]   ∣ i̸ prime[j] \ |\not i prime[j] i的时候,两者互质,满足积性函数的性质, f [ i ∗ p r i m e [ j ] ] = f [ i ] ∗ f [ p r i m e [ j ] ] f[i * prime[j]] = f[i] * f[prime[j]] f[iprime[j]]=f[i]f[prime[j]]
p r i m e [ j ]   ∣   i prime[j] \ |\ i prime[j]  i的时候, f [ i ∗ p r i m e [ j ] ] = f [ i ] ∗ p r i m e [ j ] k f[i * prime[j]] = f[i] * prime[j]^k f[iprime[j]]=f[i]prime[j]k

第二个结论和筛 φ \varphi φ函数的时候类似,下面证明一下:
p = p r i m e [ j ] p = prime[j] p=prime[j]
p [ j ]   ∣   i p[j] \ |\ i p[j]  i时,证明 i p [ j ] \frac{i}{p[j]} p[j]i i i i有相同的质因子,那么

F ( i ) F ( i p ) = p i k ( c i − 1 ) × p i k − 1... p i k ( c i − 2 ) × p i k − 1... = p k \frac{F(i)}{F(\frac{i}{p})}=\frac{p_i^{k{(ci-1)}}\times p_i^k-1...}{p_i^{k{(ci-2)}}\times p_i^k-1...}=p^k F(pi)F(i)=pik(ci2)×pik1...pik(ci1)×pik1...=pk

所以, f [ i ∗ p r i m e [ j ] ] = f [ i ] ∗ p r i m e [ j ] k f[i * prime[j]] = f[i] * prime[j]^k f[iprime[j]]=f[i]prime[j]k

#include 
#include 
#include 
#include 
#define ll long long
using namespace std;

const int N = 5e6 + 10;
const int mod = 1e9 + 7;
ll prime[N],mu[N],tot = 0,f[N] ={0},g[N] = {0};
bool prime_tag[N] = {0};
int t,k,n,m;
ll qpow(ll a,ll b){
    ll res = 1ll;
    while(b){
        if(b & 1){
            res = res * a % mod;
        }
        a = a * a % mod;
        b >>= 1;
    }
    return res;
}
void init(){
    f[1] = 1;
    for(int i = 2; i < N; i++){
        if(!prime_tag[i]){
            prime[tot] = i;
            g[tot] = qpow(i,k);
            f[i] = (g[tot]-1 + mod) % mod;
            tot++;
        }
        for(int j = 0; j < tot && i * prime[j] < N; j++){
            prime_tag[i * prime[j]] = true;
            if(i % prime[j] == 0){
                f[i * prime[j]] = (ll)f[i] * g[j] % mod;
                break;
            }else
                f[i * prime[j]] = (ll)f[i] * f[prime[j]] % mod;
        }
    }
    f[0] = 0;
    for(int i = 1; i < N; i++)
        f[i] = (f[i] + f[i-1]) % mod;

}
ll solve(){
    ll res = 0;
    for(int l = 1,r ; l <= n; l = r + 1){
        r = min(n / (n / l), m / (m / l));
        res += (f[r] - f[l - 1] + mod ) % mod  * (n / l) % mod * (m / l) % mod ;
       //printf("f[r] - f[l - 1] = %lld ,res = %lld\n",f[r] - f[l - 1],res);
    }
    return res % mod;
}
int main(){
    scanf("%d %d", &t, &k);
    init();
    while(t--) {
        scanf("%d %d", &n, &m);
        if(n > m) swap(n, m);
        printf("%lld\n", solve());
    }
    return 0;
}

【例4】P1829 [国家集训队]Crash的数字表格 / JZPTAB
题意

为了研究最小公倍数, C r a s h Crash Crash画了一张 N ∗ M N*M NM的表格,每个格子里写了一个数字,其中第 i i i行第 j j j列的那个格子里写着数 L C M ( i , j ) LCM(i,j) LCM(i,j) C r a s h Crash Crash想知道表格里所有的数的和mod 20101009的值。

思路
首先将问题转化为数学形式,保证 N < = M N<=M N<=M,如果大就进行交换:

a n s = ∑ i = 1 N ∑ j = 1 M l c m ( i , j ) ans = \displaystyle\sum_{i =1}^{N}\sum_{j = 1}^{M}lcm(i,j) ans=i=1Nj=1Mlcm(i,j)

= ∑ i = 1 N ∑ j = 1 M i ∗ j g c d ( i , j ) = \displaystyle\sum_{i =1}^{N}\sum_{j = 1}^{M}\frac{i*j}{gcd(i,j)} =i=1Nj=1Mgcd(i,j)ij

d = g c d ( i , j ) d = gcd(i,j) d=gcd(i,j),我们枚举 d d d,则:
a n s = ∑ d N 1 d ∑ i N ∑ j M i × j [   g c d ( i , j ) = = d   ] ans = \displaystyle\sum_{d}^{N}\frac{1}{d}\sum_{i}^{N}\sum_{j}^{M}i\times j[\ gcd(i,j)==d\ ] ans=dNd1iNjMi×j[ gcd(i,j)==d ]

f ( N , M , d ) = ∑ i N ∑ j M i × j [   g c d ( i , j ) = = d   ] f(N,M,d) = \displaystyle\sum_{i}^{N}\sum_{j}^{M}i\times j[\ gcd(i,j)==d\ ] f(N,M,d)=iNjMi×j[ gcd(i,j)==d ]
g ( N , M , d ) = ∑ i N ∑ j M i × j [   d   ∣   g c d ( i , j )   ] = ∑ d ∣ i N i ∑ d ∣ j M j = d 2 × ⌊ N d ⌋ ( ⌊ N d ⌋ + 1 ) 2 × ⌊ M d ⌋ ( ⌊ M d ⌋ + 1 ) 2 g(N,M,d) = \displaystyle\sum_{i}^{N}\sum_{j}^{M}i\times j[\ d\ |\ gcd(i,j)\ ]=\sum_{d|i}^{N}i\sum_{d|j}^{M}j =d^2\times\frac{\lfloor\frac{N}{d}\rfloor(\lfloor\frac{N}{d}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{d}\rfloor(\lfloor\frac{M}{d}\rfloor+1)}{2} g(N,M,d)=iNjMi×j[ d  gcd(i,j) ]=diNidjMj=d2×2dN(dN+1)×2dM(dM+1)

这里是一个循环对 j j j求和,一个循环对 i i i求和, ∑ i N ∑ j M i × j \displaystyle\sum_{i}^{N}\sum_{j}^{M}i\times j iNjMi×j ∑ i 1 ⌊ N d ⌋ ∑ j 1 ⌊ M d ⌋ d 2 × i 1 × j 1 \displaystyle\sum_{i_1}^{\lfloor\frac{N}{d}\rfloor}\sum_{j_1}^{\lfloor\frac{M}{d}\rfloor}d^2\times i_1\times j_1 i1dNj1dMd2×i1×j1等价

简要证明:首先我们知道 i ∈ [ 1 , N ] , j ∈ [ 1 , M ] i\in[1,N],j\in[1,M] i[1,N],j[1,M],满足 g c d ( i , j ) = = d gcd(i,j) == d gcd(i,j)==d 的数对个数是 ⌊ N d ⌋ × ⌊ M d ⌋ {\lfloor\frac{N}{d}\rfloor}\times{\lfloor\frac{M}{d}\rfloor} dN×dM,我们将 i , j i,j i,j 除以 d d d ,缩小了范围,将 i , j i,j i,j的范围从 [1,N] 和 [1,M] 缩小到了 [1, ⌊ N d ⌋ {\lfloor\frac{N}{d}\rfloor} dN] 和[1, ⌊ M d ⌋ {\lfloor\frac{M}{d}\rfloor} dM],变成了 i 1 , j 1 i_1,j_1 i1,j1 i = d × i 1 , j = d × j 1 i= d\times i_1,j= d\times j_1 i=d×i1,j=d×j1

开始莫比乌斯反演:

f ( d ) = ∑ d ∣ n μ ( n d ) g ( n ) = ∑ d ∣ n μ ( n d ) × n 2 × ⌊ N n ⌋ ( ⌊ N n ⌋ + 1 ) 2 × ⌊ M n ⌋ ( ⌊ M n ⌋ + 1 ) 2 f(d) = \displaystyle\sum_{d | n}\mu(\frac{n}{d})g(n)=\sum_{d | n}\mu(\frac{n}{d})\times n^2\times\frac{\lfloor\frac{N}{n}\rfloor(\lfloor\frac{N}{n}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{n}\rfloor(\lfloor\frac{M}{n}\rfloor+1)}{2} f(d)=dnμ(dn)g(n)=dnμ(dn)×n2×2nN(nN+1)×2nM(nM+1)

a n s = ∑ d = 1 N 1 d × f ( d ) ans = \displaystyle\sum_{d=1}^{N}\frac{1}{d}\times f(d) ans=d=1Nd1×f(d)
a n s = ∑ d = 1 N 1 d ∑ d ∣ n μ ( n d ) × n 2 × ⌊ N n ⌋ ( ⌊ N n ⌋ + 1 ) 2 × ⌊ M n ⌋ ( ⌊ M n ⌋ + 1 ) 2 ans = \displaystyle\sum_{d =1}^{N}\frac{1}{d}\sum_{d|n}\mu(\frac{n}{d})\times n^2\times\frac{\lfloor\frac{N}{n}\rfloor(\lfloor\frac{N}{n}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{n}\rfloor(\lfloor\frac{M}{n}\rfloor+1)}{2} ans=d=1Nd1dnμ(dn)×n2×2nN(nN+1)×2nM(nM+1)

x = n d x = \frac{n}{d} x=dn,枚举 x x x

a n s = ∑ d = 1 N 1 d ∑ x ⌊ N d ⌋ μ ( x ) × d 2 × x 2 × ⌊ N n ⌋ ( ⌊ N n ⌋ + 1 ) 2 × ⌊ M n ⌋ ( ⌊ M n ⌋ + 1 ) 2 ans = \displaystyle\sum_{d=1}^{N}\frac{1}{d}\sum_{x}^{\lfloor\frac{N}{d}\rfloor}\mu(x)\times d^2\times x^2\times \frac{\lfloor\frac{N}{n}\rfloor(\lfloor\frac{N}{n}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{n}\rfloor(\lfloor\frac{M}{n}\rfloor+1)}{2} ans=d=1Nd1xdNμ(x)×d2×x2×2nN(nN+1)×2nM(nM+1)

a n s = ∑ d = 1 N ∑ x ⌊ N d ⌋ μ ( x ) × x × n × ⌊ N n ⌋ ( ⌊ N n ⌋ + 1 ) 2 × ⌊ M n ⌋ ( ⌊ M n ⌋ + 1 ) 2 ans = \displaystyle\sum_{d=1}^{N}\sum_{x}^{\lfloor\frac{N}{d}\rfloor}\mu(x)\times x\times n\times \frac{\lfloor\frac{N}{n}\rfloor(\lfloor\frac{N}{n}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{n}\rfloor(\lfloor\frac{M}{n}\rfloor+1)}{2} ans=d=1NxdNμ(x)×x×n×2nN(nN+1)×2nM(nM+1)

a n s = ∑ n = 1 N n × ⌊ N n ⌋ ( ⌊ N n ⌋ + 1 ) 2 × ⌊ M n ⌋ ( ⌊ M n ⌋ + 1 ) 2 ∑ x ∣ n μ ( x ) × x ans = \displaystyle\sum_{n=1}^{N}n\times \frac{\lfloor\frac{N}{n}\rfloor(\lfloor\frac{N}{n}\rfloor+1)}{2}\times\frac{\lfloor\frac{M}{n}\rfloor(\lfloor\frac{M}{n}\rfloor+1)}{2}\sum_{x|n}\mu(x)\times x ans=n=1Nn×2nN(nN+1)×2nM(nM+1)xnμ(x)×x

前一部分直接可以数论整除分块,根据莫比乌斯反演的性质后一部分是一个积性函数,我们在线性筛中预处理。

f 1 ( n ) = ∑ x ∣ n μ ( x ) × x f_1(n) =\displaystyle\sum_{x|n}\mu(x)\times x f1(n)=xnμ(x)×x

根据唯一分解定理:

n = p 1 c 1 p 2 c 2 p 3 c 3 . . . p k c k n = p_1^{c1} p_2^{c2} p_3^{c3}... p_k^{ck} n=p1c1p2c2p3c3...pkck

f 1 ( n ) = f 1 ( p 1 c 1 p 2 c 2 p 3 c 3 . . . p k c k ) = ∏ i = 1 k p i c i \displaystyle f_1(n) = f_1(p_1^{c1} p_2^{c2} p_3^{c3}... p_k^{ck}) = \prod_{i=1}^{k}p_i^{ci} f1(n)=f1(p1c1p2c2p3c3...pkck)=i=1kpici

对于 f 1 ( n ) f_1(n) f1(n),当 n    i s    p r i m e n\ \ is\ \ prime n  is  prime 时,在求和的过程中,根据莫比乌斯函数的性质,只有当 x x x 只有 n , 1 n,1 n,1 两个值可取,的时候对和有贡献。所以当 n    i s    p r i m e n\ \ is\ \ prime n  is  prime 时, f 1 ( n ) = 1 − n f_1(n)=1-n f1(n)=1n

这样我们线性筛的时候就很简单了:

i   m o d   p r i m e [ j ] = = 1 i \ mod\ prime[j] == 1 i mod prime[j]==1时, f 1 ( i ∗ p r i m e [ j ] ) = f 1 ( i ) × f 1 ( p r i m e [ j ] ) f_1(i*prime[j])=f_1(i)\times f_1(prime[j]) f1(iprime[j])=f1(i)×f1(prime[j])

i   m o d   p r i m e [ j ] = = 0 i \ mod\ prime[j] == 0 i mod prime[j]==0时, f 1 ( i ∗ p r i m e [ j ] ) = f 1 ( i ) = 1 − i f_1(i*prime[j])=f_1(i)=1-i f1(iprime[j])=f1(i)=1i

p = p r i m e [ j ] p = prime[j] p=prime[j]
.
i   m o d   p = = 0 i \ mod\ p == 0 i mod p==0时, n p , n \frac{n}{p},n pn,n 都是 p p p 的倍数,
.
f 1 ( n ) f 1 ( n p ) = ( 1 − p 1 ) ( 1 − p 2 ) . . . ( 1 − p k ) ( 1 − p 1 ) ( 1 − p 2 ) . . . ( 1 − p k ) = 1 \displaystyle \frac{f_1(n)}{f_1(\frac{n}{p})}=\frac{(1-p_1)(1-p_2)...(1-p_k)}{(1-p_1)(1-p_2)...(1-p_k)}=1 f1(pn)f1(n)=(1p1)(1p2)...(1pk)(1p1)(1p2)...(1pk)=1

#include 
#include 
#include 
#include 
#define ll long long
using namespace std;

const int mod = 20101009;
const int Max = 1e7 + 10;
int prime[Max],prime_tot = 0,f[Max],s[Max];
bool prime_tag[Max] = {0};
int n,m;

void get_prime(){
	f[1] = 1;
	for(int i = 2; i < Max; i++){
		if(!prime_tag[i]){
			prime[prime_tot++] = i;
			f[i] = (1 - i + mod) % mod;
		}
		for(int j = 0 ; j < prime_tot && i * prime[j] < Max; j++){
			prime_tag[i * prime[j]]  = true;
			if(i % prime[j] == 0){
				f[i * prime[j]] = f[i];
				break;
			}else{
				f[i * prime[j]] = 1ll * f[i] * f[prime[j]] % mod ;
			}
		}
	}
	f[0] = 0;
	for(int i = 1; i < Max; i++)
		f[i] = (f[i-1]  + 1ll * f[i] * i % mod) % mod;
}
ll solve(){
	ll ans = 0,t1,t2,t3;
	for(int l = 1,r; l <= n; l = r + 1){
		r = min(n / (n / l),m / (m / l));
		t1 = 1ll *(f[r] - f[l-1] + mod ) % mod;
		t2 = 1ll * (n / l) * (n / l + 1) / 2 % mod;
		t3 = 1ll * (m / l) * (m / l + 1)  / 2 % mod;
		ans += t1 % mod * t2 % mod * t3 % mod ;
	}
	return ans % mod;
}
int main(){
	get_prime();
	scanf("%d%d",&n,&m);
	if(n > m) swap(n,m);
	printf("%lld",solve());
	return 0;
}

你可能感兴趣的:(快乐打牢基础,莫比乌斯反演)