类欧几里得算法

万恶之源spa


首先推一下能够发现,咱们能够分“位”计算。.net

设二进制下第\(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\]get

最后一步至关于第\(k\)以前的内容消掉。it

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

首先咱们能够先算一下\(\sum\limits_{i=0}^{n}\left \lfloor \dfrac{ai+b}{c} \right \rfloor\)的值(由于类欧的下标就是从\(0\))开始的。class

(设\(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\)im

di

\[\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}^{m} [\left \lfloor \dfrac{ai+b}{c} \right \rfloor \geqslant j ] $

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

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

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

将求和符号右边的式子转换一下,得$\sum\limits_{i=0}^{n}\sum\limits_{j=0}^{m-1} [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)\)

因此这就是类欧。

例题代码


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

相关文章
相关标签/搜索