[学习笔记]杜教筛

模板测试链接

传送门

〇、前言

杜教不会杜教筛.

对于一些积性函数,我们有较寻常的欧筛的 \(\mathcal O(n)\) 或者埃氏筛法的 \(\mathcal O(n\log n)\) 进行处理,但是这些算法有些弊端——比如辅助空间需要较大,以及时间复杂度不是非常优秀(都线性了还非人哉?)

比如我们的传送门,有数据范围 \(n\le 2^{31}\),这TM直接自闭,这个时候需要使用杜教筛、洲阁筛、\(\tt min\_25\) 筛等优于线性的复杂度的筛法.

壹、前置芝士

一,积性函数

对于函数 \(f(i)\) 而言,如果有 \(f(ab)=f(a)f(b)\),其中 \((a,b)=1\) 的话,那么我们称 \(f\) 为积性函数.

更强地,如果没有 \((a,b)=1\) 的限制也满足,那么称 \(f\) 为完全积性函数.

有些比较常见的积性函数,比如:

  • 莫比乌斯函数 \(\mu\),积性函数;
  • 欧拉函数 \(\varphi\),积性函数;
  • 约数个数函数 \(d\),或者说 \(\tau\) 或者 \(\sigma_0\),积性函数;
  • 约数和函数 \(\sigma\),积性函数;
  • 元函数 \(\epsilon\),有 \(\epsilon(n)=[n=1]\),迪利克雷卷积的乘法单位元,完全积性函数;
  • 恒等函数 \(I(n)=1\),完全积性函数;
  • 单位函数 \(id(n)=n\),完全积性;

二、迪利克雷卷积

定义一种卷积运算 \(*\)\(h=f*g\),即为

\[h(n)=\sum_{d|n}f(d)\times g(\frac{n}{d}) \]

它有一些性质:

  • 交换律,满足 \(f*g=g*f\)
  • 结合律,满足 \((f*g)*h=f*(g*h)\)
  • 分配律,满足 \(f*(g+h)=f*g+f*h\)
  • 对于元函数,有 \(f*\epsilon=f\)
  • 如果 \(f,g\) 都是积性函数,那么 \((f*g)\) 也是积性函数;

用一些应用来更好地理解迪利克雷卷积:

首先我们证明一下莫反,即这个经典结论:

若有 \(F(n)=\sum_{d|n}f(d)\),那么 \(f(n)=\sum_{d|n}\mu(d)F(\frac{n}{d})\).

对于 \(\mu\),我们有 \(\sum_{d\mid x}\mu(d)=[x=1]\),用狄利克雷卷积其实就是 \(\mu*I=\epsilon\),并且根据定义,我们也有 \(F(n)=\sum_{d|n}f(d)\),也就是

\[\begin{aligned} F&=f*I \\ \Leftrightarrow F*\mu&=f*I*\mu \\ \Leftrightarrow F*\mu&=f*(I*\mu) \\ \Leftrightarrow F*\mu&=f*\epsilon \\ \Leftrightarrow F*\mu&=f \\ \end{aligned} \]

然后,再根据定义,就是

\[f(n)=\sum_{d|n}\mu(d)F(\frac{n}{d}) \]

另一种形式,如果有 \(F(n)=\sum_{n|d}f(d)\),那么有

\[f(n)=\sum_{n|d}\mu(\frac{d}{n})F(d) \]

我们再证明一个东西,对于 \(\varphi\),有 \(\sum_{d|n}\varphi(d)=n\),也就是 \(\varphi*I=id\),同上面的证法,有

\[\begin{aligned} \varphi*I&=id\\ \Leftrightarrow \varphi&=id*\mu \end{aligned} \]

也就是 \(\varphi(n)=\sum_{d|n}\mu(d)\frac{n}{d}\),再通过莫反,我们有

\[id(n)=n=\sum_{d|n}\varphi(d) \]

同时也有

\[\frac{\varphi(n)}{n}=\sum_{d|n}\frac{\mu(d)}{d} \]

贰、杜教筛基本内容

一、基本公式推导

杜教筛是一种在 \(\mathcal O(n^{\frac{2}{3}})\) 的复杂度中计算出 \(S(n)=\sum_{i=1}^nf(i)\),其中 \(f\) 是积性函数.

我们构造俩函数 \(g,h\),让他们满足

\[h=f*g \]

且保证 \(h,g\) 都为积性函数.

那么我们有

\[\begin{aligned} \sum_{i=1}^nh(i)&=\sum_{i=1}^n\sum_{d|i}g(i)f(\frac{n}{i}) \\ &=\sum_{i=1}^ng(i)\sum_{j=1}^{\left \lfloor \frac{n}{i} \right \rfloor}f(j) \\ &=\sum_{i=1}^ng(i)\times S(\left \lfloor \frac{n}{i} \right \rfloor) \end{aligned} \]

我们把右边 \(i=1\) 这一项提出来,有

\[\begin{aligned} \sum_{i=1}^nh(i)&=g(1)S(n)+\sum_{i=2}^ng(i)\times S(\left \lfloor \frac{n}{i} \right \rfloor) \\ \Rightarrow g(1)S(n)&=\sum_{i=1}^nh(i)-\sum_{i=2}^ng(i)\times S(\left \lfloor \frac{n}{i} \right \rfloor) \\ \Rightarrow S(n)&=\frac{\sum_{i=1}^nh(i)-\sum_{i=2}^ng(i)\times S(\left \lfloor \frac{n}{i} \right \rfloor)}{g(1)} \end{aligned} \]

也就是说,如果我们 \(h\) 的前缀和比较好求,对于带 \(S\) 的部分我们可以数论分块+迭代做,这样就可以求 \(S(n)\) 了.

另一个问题,如何构造 \(h,g\) ?只能手推+经验了......

二、代码实现细节

关于杜教筛为什么是 \(\mathcal O(n^{2\over 3})\),由于涉及积分所以我无法证明,但是正是为了实现这个复杂度,在代码实现的时候,我们需要将所要求的 \(S\)(前缀和函数)的前 \(n^{2\over 3}\) 项用线性筛之类的方式筛出来才能够达到这个复杂度下界.

叁、例题

模板

[BZOJ4916]神犇和蒟蒻

[CQOI2015]选数

[luoguP3768]简单的数学题

posted @ 2021-01-31 15:37  Arextre  阅读(126)  评论(0编辑  收藏  举报