莫比乌斯反演

简介

当一个函数 f(x) f ( x ) 计算十分复杂时,如果方便计算出它的倍数的和,或因数的和 g(x) g ( x ) ,可先计算出 g(x) g ( x ) ,再通过莫比乌斯反演计算出 f(x) f ( x )
例子:
g(1)=f(1) g ( 1 ) = f ( 1 )
g(2)=f(1)+f(2) g ( 2 ) = f ( 1 ) + f ( 2 )
g(3)=f(1)+f(3) g ( 3 ) = f ( 1 ) + f ( 3 )
g(4)=f(1)+f(2)+f(4) g ( 4 ) = f ( 1 ) + f ( 2 ) + f ( 4 )
g(5)=f(1)+f(5) g ( 5 ) = f ( 1 ) + f ( 5 )
g(6)=f(1)+f(2)+f(3)+f(6) g ( 6 ) = f ( 1 ) + f ( 2 ) + f ( 3 ) + f ( 6 )
g(7)=f(1)+f(7) g ( 7 ) = f ( 1 ) + f ( 7 )
g(8)=f(1)+f(2)+f(4)+f(8) g ( 8 ) = f ( 1 ) + f ( 2 ) + f ( 4 ) + f ( 8 )

莫比乌斯反演:

将上面的例子倒回来算
f(1)=g(1) f ( 1 ) = g ( 1 )
f(2)=g(2)g(1) f ( 2 ) = g ( 2 ) − g ( 1 )
f(3)=g(3)g(1) f ( 3 ) = g ( 3 ) − g ( 1 )
f(4)=g(4)g(2) f ( 4 ) = g ( 4 ) − g ( 2 )
f(5)=g(5)g(1) f ( 5 ) = g ( 5 ) − g ( 1 )
f(6)=g(6)g(3)g(2)+g(1) f ( 6 ) = g ( 6 ) − g ( 3 ) − g ( 2 ) + g ( 1 )
f(7)=g(7)g(1) f ( 7 ) = g ( 7 ) − g ( 1 )
f(8)=g(8)g(4) f ( 8 ) = g ( 8 ) − g ( 4 )
反演公式(待证):

f(x)=i|xμ(i)g(xi) f ( x ) = ∑ i | x μ ( i ) g ( x i )

莫比乌斯函数

这里有个神奇的东西: μ(i) μ ( i ) 是莫比乌斯函数:
μ(1)=1 μ ( 1 ) = 1 μ(2)=1 μ ( 2 ) = − 1 μ(3)=1 μ ( 3 ) = − 1 μ(4)=0 μ ( 4 ) = 0 ……
定义如下:

  1. μ(1)=1 μ ( 1 ) = 1
  2. 当x分解质因数后,所有质因数的指数为1,那么 μ(x)=(1)k μ ( x ) = ( − 1 ) k (k为将x分解质因数后,质因数的个数)
  3. 当x分解质因数后,有质因数的指数>1,那么 μ(x)=0 μ ( x ) = 0
    (为什么这样定义:实际上是容斥原理,有些问题,先加上含一个质因子的所有数,减去含两个质因子的所有数,加上含三个质因子的所有数……正好使用莫比乌斯函数,方便快捷!)
性质
  • d|nμ(d)=0(n>1)1(n=1) ∑ d | n μ ( d ) = 0 ( n > 1 ) 或 1 ( n = 1 )

    证明:将n分解 n=pa11pa22pa33...pakk n = p 1 a 1 p 2 a 2 p 3 a 3 . . . p k a k
    根据定义,只有在k个p里取,每个p指数为1时才有效,取奇数个为-1,去偶数个为1
    d|nμ(d)=C0kC1k+C2k...+(1)kCkk=i=0n(1)iCin=0 ∑ d | n μ ( d ) = C k 0 − C k 1 + C k 2 − . . . + ( − 1 ) k C k k = ∑ i = 0 n ( − 1 ) i C n i = 0
    (二项式定理,当x=1,y=-1, (x+y)n= ( x + y ) n = 上面那一坨)

  • 积性函数:

    μ(xy)=μ(x)μ(y) μ ( x y ) = μ ( x ) μ ( y )

筛法求莫比乌斯函数

所以可以用线性筛的方法筛出莫比乌斯函数:

mu[1]=1;
for(i=2;i<=n;i++)
{
    if(!not_prime[i])
    {
        prime[++tot]=i;
        mu[i]=-1;
    }
    for(j=1;prime[j]*i<=n;j++)
    {
        not_prime[prime[j]*i]=1;
        if(i%prime[j]==0)
        {
            mu[prime[j]*i]=0;
            break;
        }
        mu[prime[j]*i]=-mu[i];
    }
}

反演函数证明

现在倒回来证明开始那个反演函数:

g(x)=i|xf(i) g ( x ) = ∑ i | x f ( i )

证明:
f(x)=i|xμ(i)g(xi)=i|xμ(i)j|xif(j)=i|xij|xμ(i)f(j)=j|xij|xμ(i)f(j)=j|xf(j)i|xjμ(i) f ( x ) = ∑ i | x μ ( i ) g ( x i ) = ∑ i | x μ ( i ) ∑ j | x i f ( j ) = ∑ i | x ∑ i j | x μ ( i ) f ( j ) = ∑ j | x ∑ i j | x μ ( i ) f ( j ) = ∑ j | x f ( j ) ∑ i | x j μ ( i )

根据性质,当 xj=1 x j = 1 i|xjμ(i)=1 ∑ i | x j μ ( i ) = 1 ,其他时候等于0.
f(x)=j|xf(j)i|xjμ(i)=f(x) f ( x ) = ∑ j | x f ( j ) ∑ i | x j μ ( i ) = f ( x )

分块优化

实际题目中,直接跑莫比乌斯反演暴力一般是要超时的。。。(尴尬,,ԾㅂԾ,,),一般都要加优化。主要有一个分块思想。
分块
很多题都是这种情况(一般涉及gcd),绿色代表 nkd n k d 相等,蓝色部分代表 mkd m k d 相等,红色部分代表两个都相等。这样,再同一个红色块的就可以一次计算,所以我们需要预处理 μ(d) μ ( d ) 的前缀和,用last=min(n/(n/d),m/(m/d));计算出当前红块的结尾位置,就可以把时间优化到 O(n+m) O ( n + m )

if(n>m) swap(n,m);
for(i=1;i<=n;i=last+1)
{
    last=min(n/(n/i),m/(m/i));
    re+=(n/i)*(m/i)*(sum[last]-sum[i-1]);
}
return re;
  • 3
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值