一本通OJ-方案统计
方案统计
题意
求\(C[n][m]\pmod{P}\)。
分析
求逆元。
\(a*a^-1\equiv1\pmod{m}\) 则称\(a^-1\)是\(a\)在模\(m\)意义下的逆元。
求法:
-
\(p\log{p}\)。
由费马小定理可得,若\(m\)为质数,则有\(a*a^{m-2}\equiv1\pmod{m}\)。
则\(a^{m-2}\)为逆元。可以使用快速幂。
-
\(p\)。
设\(m=\)\(\left\lfloor\dfrac{m}{x}\right\rfloor*x+r\)。则有\(x>r\)。
转化为\(\left\lfloor\dfrac{m}{x}\right\rfloor*x+r\equiv{0}\pmod{m}\)
同乘\(x^{-1}r{-1}\)。则有\(\left\lfloor\dfrac{m}{x}\right\rfloor*r^{-1}+x^{-1}\equiv{0}\pmod{m}\)
得\(x^{-1}\equiv{-\left\lfloor\dfrac{m}{x}\right\rfloor*r^{-1}}\pmod{m}\)。
显然\(r<x\)则\(r^{-1}\)已知。
\(r=m-\left\lfloor\dfrac{m}{x}\right\rfloor*x\)。
显然\(r=m \mod {x}\)。
inv[1]=1; for(int i=2;i<=n;i++){ inv[i]=((p-p/i)*inv[p%i]+p)%p; }
求\(O(1)\)组合数
\(C_{n}^{m}={n!}*(m!)^{-1}*(n-m)!^{-1}\)
注意到可以直接递归求出\(n!\)。而后\(m!^{-1}=(m-1)!^{-1}*m^{-1}\mod{p}\)。
又因为\(m,n\)范围,不可能暴力求。
卢卡斯定理
\(C_{n}^{m}\mod{p}=C_{n\mod{p}}^{m\mod{p}}*C_{n/p}^{m/p}{\mod{p}}\)。
前项显然均小于\(p\)。后一项递归求即可。
代码
void init(){
fac[0]=inv[0]=fac[1]=inv[1]=1;
for(int i=2;i<=mod;i++){
fac[i]=fac[i-1]*i%mod;
inv[i]=((mod-mod/i)*inv[mod%i]+mod)%mod;
}
for(int i=2;i<=mod;i++) inv[i]=inv[i-1]*inv[i]%mod;
}
int C(int n,int m){
if(n<m) return 0;
return fac[n]*inv[m]%mod*inv[n-m]%mod;
}
int lucas(int n,int m){
if(m==0) return 1;
else return C(n%mod,m%mod)*lucas(n/mod,m/mod)%mod;
}