组合数取模

明确一下,我们要求这个:

\[{n \choose m} \bmod t \]

defs

假设\(n,m,t \le 2^w\),\(w\)是字长,即认为+-×÷全是basic operation(\(O(1)\)).

\[{n \choose m} = \frac{n^{\underline{m}}}{m!} = \frac{n}{(m-n)!m!} \]

\[R_p(x)$$为$x$的质因数分解中质因数$p$的次数,若$p$不是质数则$R_p(x)=0$.可以在$O(\log_p{n})$的时间复杂度内求出. $$primes = \mathtt{Set~of~primes.}\]

\[pr(x) = [x \in primes] \]

algos

\(pr(t)~~t,n,m \le 10^9\)

预处理阶乘与阶乘逆元.

\(pr(t)~~t\le 10^9, n,m\le 10^{18}\)

Lucas定理.

\({n \choose m}\equiv {\lfloor n/t \rfloor \choose \lfloor m/t \rfloor} {n \bmod t \choose m \bmod t} \pmod{t}\)

\(O(n),O(\log{n})\)

Chinese remainder theorem(CRT)

解方程组\(\mathtt{Constraint:~}\forall i\not= j,\gcd{i,j}=1,\mathtt{Equations:~}\forall i,x\equiv y_i\pmod{t_i}\)

(有点显然,但是需要证明)\(x\equiv \sum_i y_i b_i \frac{\prod_j t_j}{t_i} \pmod{\prod_j t_j}\),其中\(b_i=\left(\left( \prod_j t_j \right) / t_i\right)^{-1} \bmod t_i\),大概考虑下贡献什么的就能理解它的正确性.

\(pr(t)~~t\le 10^{10}, n,m\le 10^{18}\)

前置技能FFT mod any prime,多项式多点求值.(而且数据范围略鬼畜,好自为之吧(如果你要去写的话= =))

考虑如何求出阶乘,构造多项式\(f_n(x)=\prod_{i=1}^n(x+i)\),显然\(n!=f_n(0)\).我们考虑如何计算.那么我们考虑\(f_n(0)=\prod_{i=0}^mf_m(im)\)(其中\(n\)=\(m^2\)),如果不是\(n\)完全平方数只会剩下\(O(\sqrt{n})\)项,暴力做,不然就先把这个式子求出来,多点求值一下.复杂度是\(O(\sqrt{n}\log^2{n})\),当然做\(n,m\le 10^{18}\)就顺手Lucas一发(求两次).如果你有工业级的工具可以去试试.

\(t=p^q, pr(p)\)

\(q=1\)用上面的算法,否则\(p\)不太大.

首先用\(R\)函数处理掉答案的\(p\)因子,现在问题是求\(f_n\bmod{p^q}\).我们发现这时的\(f_n\)最高次项最多是\(q-1\)次(显然).考虑倍增\(f_n\).

\(f_{2px+d}=f_{px}f_{px}(px)f_d(2px)\).其中\(d\le p\),那么复杂度是\(O(q^2)\)倍增一次,总共\(O(\log{n})\)次,加上预处理\(f_d\)总复杂度\(O(q^2\log{n}+pq)\).

这里计算都是纯暴力计算.大约可以优化一下但是因为p不会很大应该也只有优化\(f_d\)的计算会有些实际意义.

没有性质的题目

CRT+上面的算法+一些优化.

常数优化

然而我们的\(f_n\)函数可以直接求下降幂,常数/1.5 get.

为什么\(O(n)\)能跑\(10^9\)

假设是题答/PE环境.

posted @ 2016-07-15 23:07  zball  阅读(337)  评论(0编辑  收藏  举报