积性筛

一些定义

  • 数论函数:定义域为正整数的函数。
  • 积性函数:满足\(f(a)f(b)=f(ab)\ (gcd(a,b)=1)\)的数论函数。
  • 积性筛:在低于线性的时间内求出积性函数前缀和的奇妙算法。

一些积性函数

  • \(\varphi(x)\):欧拉函数。
  • \(\mu(x)\):莫比乌斯函数。
  • \(\epsilon(x)\):元函数。\(\epsilon(x)=\delta_{x1}\)
  • \(d(x)\):约数函数。\(d(x)=\sum_{d|x}1\)
  • \(\sigma(x)\):约数和函数。\(\sigma(x)=\sum_{d|x}d\)
  • \(I(x)\):恒等函数。\(I(x)=1\)
  • \(id(x)\):单位函数。\(id(x)=x\)

狄利克雷卷积

  • 两个数论函数\(f(x),g(x)\)的狄利克雷卷积定义为:\(f*g=\sum_{d|n}f(d)g(\frac nd)\)
  • 显然,狄利克雷卷积满足交换律、结合律、分配律。并且我们不难发现一个性质:两个积性函数的狄利克雷卷积依然是积性函数。

杜教筛

  • 发明dalao:%杜%瑜%皓%

算法流程

  • \(S(n)=\sum_{i=1}^n f(i)\)。我们要求一个\(S(n)\)
  • 设有另一个积性函数\(g\),并设\(h=f*g\),则有:\[\sum_{i=1}^nh(i)=\sum_{i=1}^n\sum_{d|i}f(d)g(\frac id)=\sum_{d=1}^ng(d)\sum_{i=1}^{\lfloor\frac nd\rfloor}f(i)=\sum_{d=1}^ng(d)S(\lfloor\frac nd\rfloor)\]
  • 因此,\(g(1)S(n)=\sum_{i=1}^nh(i)-\sum_{d=2}^ng(d)S(\lfloor\frac nd\rfloor)\)
  • 由于\(g\)是积性函数,\(g(1)=1\),所以\(S(n)\)就等于右式。

  • 对于\(\sum h(i)\),我们要有一个快速求它的算法(一般要求时间不超\(O(\sqrt n)\));而对于被减数,我们可以先分块,然后递归求解\(S(\lfloor\frac nd\rfloor)\)。由于\(\lfloor\frac {\lfloor\frac ab\rfloor}c\rfloor=\lfloor\frac a{bc}\rfloor\),我们算过的\(S(x)\)一定满足\(x=\lfloor\frac nd\rfloor(d\in[1,n])\),故可以用两个桶(一个是\(≤\sqrt n\)的,一个是\(>\sqrt n\)的,当然也可以合成一个桶)记忆化一下。
  • 空间复杂度显然\(O(\sqrt n)\)
  • 时间的话,可以发现\(x=\lfloor\frac nd\rfloor(d\in[1,n])\)只有\(O(\sqrt n)\)种取值,而且它们都是算过一次就不再算了(记忆化)。因此,\(T(n)=\sum_{i=1}^{\sqrt n}O(\sqrt i)+O(\sqrt{\lfloor\frac ni\rfloor})\)。可以求一个定积分,便知\(T(n)=O(n^{\frac 34})\)。也就是说,我们大概可以撵过\(n=10^{10}\)的数据,但\(n=10^{11}\)时就有点玄了。

简单例题

T1
  • \(S(n)=\sum_{i=1}^n\mu(i)\)
  • 我们知道\(\mu\)有个性质:\(\mu*I=\epsilon\)。那么直接套公式便可得:\(S(n)=1-\sum_{d=2}^nS(\lfloor\frac nd\rfloor)\)
T2
  • 定义\(f(n)=n\varphi(n)\),求\(S(n)=\sum_{i=1}^nf(i)\)
  • \(h=f*id\),可知\(h(n)=\sum_{d|n}n\varphi(d)=n^2\)。则:\(S(n)=\frac{n(n+1)(2n+1)}6-\sum_{d=2}^ndS(\lfloor\frac nd\rfloor)\)
T3:51nod2026
  • 题目其实是要求\((S(n)=\sum_{i=1}^nf(i))^2\)
  • 稍微推一下式子,\(S(n)=\sum_{i=1}^n\sum_{d|i}d\mu(d)=\sum_{d=1}^nd\mu(d)\lfloor\frac nd\rfloor\)。后面\(\lfloor\frac nd\rfloor\)可以分块来处理,现在我们要处理的只是若干个\(s(x)=\sum_{d=1}^xd\mu(d)\)而已(而且这些\(x\)也都是\(n\)整除某一个数得来)。
  • 依然让它卷上\(id\)\(h(n)=\sum_{d|n}n\mu(d)=\epsilon(n)\)。则:\(s(n)=1-\sum_{d=2}^ndS(\lfloor\frac nd\rfloor)\)
#include <cmath>
#include <cstdio>
#define fo(i,a,b) for(int i=a;i<=b;i++)
using namespace std;

const int M=1e5,N=2e5,mo=1e9+7;
int n,k,s[N],S;
bool v[N];

int C(int x) {return x<=k?M+x:n/x;}
int P(int&x,int y) {x=(1ll*x+y)%mo;}
void gets(int x)
{
    v[C(x)]=s[C(x)]=1;
    for(int i,l=2,r; l<=x; l=r+1)
    {
        r=x/(i=x/l);
        if(!v[C(i)]) gets(i);
        P(s[C(x)],mo-1ll*(l+r)*(r-l+1)/2%mo*s[C(i)]%mo);
    }
}

int main()
{
    scanf("%d",&n), k=sqrt(n);
    gets(n);
    for(int i,l=1,r; l<=n; l=r+1)
    {
        r=n/(i=n/l);
        P(S,1ll*i*(1ll*mo+s[C(r)]-s[C(l-1)])%mo);
    }
    printf("%lld",1ll*S*S%mo);
}

min25筛

  • 发明dalao:%m%i%n%2%5%

猜你喜欢

转载自www.cnblogs.com/Iking123/p/11593443.html