类欧几里得算法

万恶之源


首先推一下可以发现,我们可以分“位”计算。

设二进制下第\(k\)对答案的贡献为\(\mathrm{Ans_k}\),则

\[\mathrm{Ans_k=}\sum\limits_{i=1}^{n} \texttt{“ai+b的第k位为1”}=\sum\limits_{i=1}^{n} \left \lfloor \frac{ai+b}{2^{k}} \right \rfloor \bmod 2 =\sum\limits_{i=1}^{n} \left \lfloor \frac{ai+b}{2^{k}} \right \rfloor - 2\left \lfloor \frac{ai+b}{2^{k+1}} \right \rfloor \]

最后一步相当于第\(k\)之前的内容消掉。

然后就引出了一个通用的问题:如何快速地求出\(\sum\limits_{i=0}^{n}\left \lfloor \dfrac{ai+b}{c} \right \rfloor\)的值。

首先我们可以先算一下\(\sum\limits_{i=0}^{n}\left \lfloor \dfrac{ai+b}{c} \right \rfloor\)的值(因为类欧的下标就是从\(0\))开始的。

(设\(f(a,b,c,n)=\sum\limits_{i=0}^{n} \left \lfloor \dfrac{ai+b}{c} \right \rfloor\)

\(\left \lfloor \dfrac{ai+b}{c} \right \rfloor\)可能是个假分数,所以我们可以把它拆成一个带分数。

\(a'=a \mod c\)\(b'=b \mod c\)

\[\sum\limits_{i=0}^{n}\left \lfloor \dfrac{ai+b}{c} \right \rfloor=\left \lfloor \frac{a'i+b'}{c} \right \rfloor +i \left \lfloor \frac{a}{c} \right \rfloor+\left \lfloor \frac{b}{c} \right \rfloor = f(a',b',c,n)+\dfrac{(n+1)n}{2}\left \lfloor \frac{a}{c} \right \rfloor+(n+1)\left \lfloor \frac{b}{c} \right \rfloor \]


对于\(a<c,b<c\)的情况,我们就再次乱搞

(设\(m=\left \lfloor \dfrac{an+b}{c} \right \rfloor\)

那么$f(a,b,c,n) =\sum\limits_{i=0}{n}\sum\limits_{j=1} [\left \lfloor \dfrac{ai+b}{c} \right \rfloor \geqslant j ] $

这一步貌似把原式变复杂了,但是接下来就会发觉这是有用的。

接着,我们把\(j\)的下标改一改:$\sum\limits_{i=0}{n}\sum\limits_{j=0} [\left \lfloor \dfrac{ai+b}{c} \right \rfloor \geqslant j+1 ] $

很好,接下来就开始秀操作了。

将求和符号右边的式子转换一下,得$\sum\limits_{i=0}{n}\sum\limits_{j=0} [i \geqslant \dfrac{jc+c-b}{a} ] $

把第一个求和符号去掉(因为方框里面那个只是\(bool\)变量,完全可以换成差式),再把不等式的符号改成大于号,得

$\sum\limits_{j=0}^{m-1} n- \left \lfloor \dfrac{jc+c-b-1}{a} \right \rfloor $

这里多了个\(-1\)是因为$x \geqslant y \Rightarrow x>y-1 $,然后向下取整消失了又出现是正确的,这里真的不想解释。

然后有没有发现$\left \lfloor \dfrac{jc+c-b-1}{a} \right \rfloor \(和\)f$的定义很像?

没错!这就说明我们的变换成功了!

将上面式子中的\(n\)提出求和符号,再将\(f\)代入,得

\(nm-f(c,c-b-1,a,m-1)\)

所以这就是类欧。

例题代码


当然了,类欧的基本式子还可以加上指数和系数,这个有空再更。

posted @ 2019-07-31 19:41  info___tion  阅读(192)  评论(0编辑  收藏  举报