数论-卢卡斯定理(lucas)与拓展卢卡斯定理 (exlucas)
卢卡斯定理(lucas)
[用途]
求解 C n m % p C_{n}^{m}\% p Cnm%p,其中m,n较大,p较小且为素数
[结论]
C n m ≡ C n / p m / p C n % p m % p ( m o d p ) C_{n}^{m}\equiv C_{n/p}^{m/p}C_{n\%p}^{m\%p}(mod \quad p) Cnm≡Cn/pm/pCn%pm%p(modp)
[证明]
假设: { n = s p + q m = t p + r \left\{\begin{array}{cc} n=sp+q\\ m=tp+r \end{array}\right. {n=sp+qm=tp+r
即证明 C n m ≡ C s t C q r ( m o d p ) C_{n}^{m}\equiv C_{s}^{t}C_{q}^{r}(mod \quad p) Cnm≡CstCqr(modp)
使用构造法:
( 1 + x ) n ≡ ( 1 + x ) s p + q ≡ [ ( 1 + x ) p ] s ( 1 + x ) q ( m o d p ) (1+x)^{n}\equiv(1+x)^{sp+q}\equiv[(1+x)^{p}]^{s}(1+x)^{q}(mod \quad p) (1+x)n≡(1+x)sp+q≡[(1+x)p]s(1+x)q(modp)
根据二项式定理
( 1 + x ) p = ∑ i = 0 p C p i x i (1+x)^{p}=\sum\limits_{i=0}^p{C_{p}^{i}x^{i}} (1+x)p=i=0∑pCpixi
除了第一项 C p 0 x 0 ( 即 1 ) C_{p}^{0}x^{0}(即1) Cp0x0(即1)与最后一项 C p p x p ( 即 x p ) C_{p}^{p}x^{p}(即x^{p}) Cppxp(即xp)不能整除p,中间项均能整除p,所以在 ( m o d p ) (mod \quad p) (modp)意义下 ( 1 + x ) p = 1 + x p (1+x)^{p}=1+x^{p} (1+x)p=1+xp
则 ( 1 + x ) n ≡ [ ( 1 + x ) p ] s ( 1 + x ) q ≡ ( 1 + x p ) s ( 1 + x ) q ( m o d p ) (1+x)^{n}\equiv[(1+x)^{p}]^{s}(1+x)^{q}\equiv(1+x^{p})^{s}(1+x)^{q}(mod \quad p) (1+x)n≡[(1+x)p]s(1+x)q≡(1+xp)s(1+x)q(modp)
即 ∑ k = 0 n C n k x k ≡ ∑ i = 0 s C s i x p i ∑ j = 0 q C q j x j ( m o d p ) \sum\limits_{k=0}^n{C_{n}^{k}x^{k}}\equiv\sum\limits_{i=0}^s{C_{s}^{i}x^{pi}}\sum\limits_{j=0}^q{C_{q}^{j}x^{j}}(mod \quad p) k=0∑nCnkxk≡i=0∑sCsixpij=0∑qCqjxj(modp)
我们在等式两边找 x m x^m xm项的系数
左:含 x m x^m xm项显然是 C n m C_{n}^{m} Cnm
右:含 x m x^m xm项只能由 x p i x j = x p i + j x^{pi}x^{j}=x^{pi+j} xpixj=xpi+j得到,即 m = p i + j m=pi+j m=pi+j,显然 i = t , j = r i=t,j=r i=t,j=r,此时对应系数恰好是 C s t C q r C_{s}^{t}C_{q}^{r} CstCqr
所以 C n m ≡ C s t C q r ( m o d p ) C_{n}^{m}\equiv C_{s}^{t}C_{q}^{r}(mod \quad p) Cnm≡CstCqr(modp)成立
即 C n m ≡ C n / p m / p C n % p m % p ( m o d p ) C_{n}^{m}\equiv C_{n/p}^{m/p}C_{n\%p}^{m\%p}(mod \quad p) Cnm≡Cn/pm/pCn%pm%p(modp)
[代码]
#include<iostream>
using namespace std;
typedef long long LL;
const LL N=1e5+2;
LL a[N];
void init(LL p)
{a[1]=1;for(int i=2;i<=p;++i)a[i]=a[i-1]*i%p;
}
void exgcd(LL a,LL b,LL &x,LL &y)
{if(!b){x=1;y=0;return;}exgcd(b,a%b,y,x);y-=a/b*x;
}
LL ksm(LL x,LL n,LL mod)
{LL ans=1;while(n){if(n&1)ans=ans*x%mod;n>>=1;x=x*x%mod;}return ans;
}
LL C(LL n,LL m,LL p)
{if(n==m||m==0)return 1;if(n<m)return 0;if(m*2>n)m=n-m; /*C(n,m)=c(n,n-m)*/return a[n]*ksm(a[m]*a[n-m],p-2,p)%p; /*求(a[m]*a[n-m])在(mod p)意义下的乘法逆元*//*拓展欧几里得与费马小定理均可*/ /*LL x,y;exgcd(a[m]*a[n-m],p,x,y);return (a[n]*x%p+p)%p;*/
}
LL lucas(LL n,LL m,LL p)
{if(!m)return 1;return lucas(n/p,m/p,p)*C(n%p,m%p,p)%p;
}
int main()
{ios::sync_with_stdio(false);LL T,n,m,p;cin>>T;while(T--){cin>>n>>m>>p;init(p);cout<<lucas(n+m,m,p)<<endl;}return 0;
}
拓展卢卡斯定理(exlucas)
[用途]
求解 C n m % P C_{n}^{m}\% P Cnm%P,其中m,n较大,P较小且不一定为素数
[解析]
转化为中国剩余定理(crt)
根据算术基本定理
P = M 1 M 2 . . . M k = ∏ i = 0 k M i P=M_{1}M_{2}...M_{k}=\prod\limits_{i=0}^{k}M_{i} P=M1M2...Mk=i=0∏kMi
其中 M i = p i t i , M i M j ( i ! = j ) M_{i}=p_{i}^{t_{i}},M_{i}M_{j}(i!=j) Mi=piti,MiMj(i!=j)两两互素
设 X = C n m X=C_{n}^{m} X=Cnm
则 A i = C n m % M i A_{i}=C_{n}^{m}\%M_{i} Ai=Cnm%Mi
所以转化为中国剩余定理
X ≡ { A 1 ( m o d M 1 ) A 2 ( m o d M 2 ) . . . A k ( m o d M k ) X\ \equiv\left\{\begin{array}{cc} A_{1} \quad (mod \quad M_{1})\\ A_{2} \quad (mod \quad M_{2})\\ ...\\ A_{k} \quad (mod \quad M_{k}) \end{array}\right. X ≡⎩⎪⎪⎨⎪⎪⎧A1(modM1)A2(modM2)...Ak(modMk)
M i M_{i} Mi根据算术基本定理循环分解即可
重点的是 A i A_{i} Ai
A i = C n m % M i = n ! m ! ( n − m ) ! % M i \begin{aligned}A_{i} &=C_{n}^{m}\%M_{i}\\ &=\frac{n!}{m!(n-m)!}\%M_{i}\\ \end{aligned} Ai=Cnm%Mi=m!(n−m)!n!%Mi
可惜的是 m ! ( n − m ) ! 在 模 M i ( M i = p i t i ) m!(n-m)!在模M_{i}(M_i=p_{i}^{t_{i}}) m!(n−m)!在模Mi(Mi=piti)意义下的乘法逆元不一定存在
我们可以先把阶层中含 p i p_{i} pi的项约去,这样就可以求逆元了,然后再乘回来即可
所以
A i = n ! m ! ( n − m ) ! % M i = n ! p i m ! p i ( n − m ) ! p i p i k % M i = n ! p i i n v ( m ! p i , M i ) i n v ( ( n − m ) ! p i , M i ) p i k % M i = ( n ! p i % M i ) i n v ( m ! p i % M i , M i ) i n v ( ( n − m ) ! p i % M i , M i ) p i k % M i \begin{aligned}A_{i} &=\frac{n!}{m!(n-m)!}\%M_{i}\\ &=\frac{\frac{n!}{p_i}}{\frac{m!}{p_i}\frac{(n-m)!}{p_i}}p_i^k\%M_{i}\\ &=\frac{n!}{p_i}inv(\frac{m!}{p_i},M_i)inv(\frac{(n-m)!}{p_i},M_i)p_i^k\%M_{i}\\ &=(\frac{n!}{p_i}\%M_{i})inv(\frac{m!}{p_i}\%M_{i},M_i)inv(\frac{(n-m)!}{p_i}\%M_{i},M_i)p_i^k\%M_{i} \end{aligned} Ai=m!(n−m)!n!%Mi=pim!pi(n−m)!pin!pik%Mi=pin!inv(pim!,Mi)inv(pi(n−m)!,Mi)pik%Mi=(pin!%Mi)inv(pim!%Mi,Mi)inv(pi(n−m)!%Mi,Mi)pik%Mi
令
n n = n ! p i % M i nn=\frac{n!}{p_i}\%M_{i} nn=pin!%Mi
m m = m ! p i % M i mm=\frac{m!}{p_i}\%M_{i} mm=pim!%Mi
n m = ( n − m ) ! p i % M i nm=\frac{(n-m)!}{p_i}\%M_{i} nm=pi(n−m)!%Mi
则 A i = n n ∗ i n v ( m m , M i ) ∗ i n v ( n m , M i ) ∗ p i k % M i A_i=nn*inv(mm,M_i)*inv(nm,M_i)*p_i^k\%M_i Ai=nn∗inv(mm,Mi)∗inv(nm,Mi)∗pik%Mi
现在的关键又转换为求 n n , m m , n m nn,mm,nm nn,mm,nm了
就nn来看
当n=19时, p i = 3 , t i = 2 p_i=3,t_i=2 pi=3,ti=2
n ! = 1 ∗ . . . ∗ 19 = 3 6 ∗ 6 ! ∗ [ ( 1 ∗ 2 ∗ 4 ∗ 5 ∗ 7 ∗ 8 ) ∗ ( 10 ∗ 11 ∗ 13 ∗ 14 ∗ 16 ∗ 17 ) ∗ 19 ) ] n!=1*...*19=3^6*6!*[(1*2*4*5*7*8)*(10*11*13*14*16*17)*19)] n!=1∗...∗19=36∗6!∗[(1∗2∗4∗5∗7∗8)∗(10∗11∗13∗14∗16∗17)∗19)]
n ! p i % M i = [ ( 1 ∗ 2 ∗ 4 ∗ 5 ∗ 7 ∗ 8 ) ∗ ( 10 ∗ 11 ∗ 13 ∗ 14 ∗ 16 ∗ 17 ) ∗ 19 ) ] ∗ 6 ! % M i \frac{n!}{p_i}\%M_{i}=[(1*2*4*5*7*8)*(10*11*13*14*16*17)*19)]*6!\%M_i pin!%Mi=[(1∗2∗4∗5∗7∗8)∗(10∗11∗13∗14∗16∗17)∗19)]∗6!%Mi
而中括号这一堆是有循环节的 1 ∗ 2 ∗ 4 ∗ 5 ∗ 7 ∗ 8 ≡ 10 ∗ 11 ∗ 13 ∗ 14 ∗ 16 ∗ 17 ( m o d M i ) 1*2*4*5*7*8\equiv10*11*13*14*16*17(mod\quad M_i) 1∗2∗4∗5∗7∗8≡10∗11∗13∗14∗16∗17(modMi)
循环节为 n / M i n/M_i n/Mi,循环一组后然后快速幂就行了
剩下的个数就是 n % M i n\%M_i n%Mi这一类直接循环相乘
而 6 ! 6! 6!恰好是 ( n / p i ) ! (n/p_i)! (n/pi)!,直接递归即可
即 n ! p i % M i = [ . . . ] ∗ ( n / p i ) ! p i % M i \frac{n!}{p_i}\%M_{i}=[...]*\frac{(n/p_i)!}{p_i}\%M_{i} pin!%Mi=[...]∗pi(n/pi)!%Mi
[ . . . ] [...] [...]就是上面的循环节那块,分类进行求解,over!
[代码]
#include<bits/stdc++.h>
using namespace std;
typedef long long LL;
const LL N=1e5+9;
LL A[N],M[N];
LL ksm(LL x,LL n,LL mod)
{LL ans=1;while(n){if(n&1)ans=ans*x%mod;n>>=1,x=x*x%mod;}return ans;
}
void exgcd(LL a,LL b,LL &x,LL &y)
{if(!b)x=1,y=0;else exgcd(b,a%b,y,x),y-=a/b*x;
}
LL inv(LL a,LL p)
{LL x,y;exgcd(a,p,x,y);return (x+p)%p?x:x+p;
}
LL get(LL n,LL pi,LL p) /*求(与pi互素后的n!)%M[i]*/
{if(!n)return 1;LL ans=1;if(n/p){ /*判断有无循环节 */ for(LL i=2;i<=p;++i)if(i%pi)ans=ans*i%p;ans=ksm(ans,n/p,p);}for(LL i=2;i<=n%p;++i)if(i%pi)ans=ans*i%p; /*循环节剩余部分*/ return ans*get(n/pi,pi,p)%p;
}
LL exlucas(LL n,LL m,LL pi,LL p) /*求A[i]*/
{LL nn=get(n,pi,p); /*求(与pi互素后的n)%M[i]*/ LL mm=get(m,pi,p); /*求(m!与pi互素后的m!)%M[i]*/ LL nm=get(n-m,pi,p); /*求(与pi互素后的(n-m)!)%M[i]*/ LL k=0; /*含质因数pi的数量*/ for(LL i=n;i;i/=pi)k+=i/pi;for(LL i=m;i;i/=pi)k-=i/pi;for(LL i=n-m;i;i/=pi)k-=i/pi;return nn*inv(mm,p)*inv(nm,p)*ksm(pi,k,p)%p;
}
LL crt(LL len,LL Lcm)
{LL ans=0;for(LL i=1;i<=len;++i){LL Mi=Lcm/M[i];ans=((ans+A[i]*inv(Mi,M[i])*Mi)%Lcm+Lcm)%Lcm;}return ans;
}
int main()
{ios::sync_with_stdio(false);LL n,m,P,num;while(cin>>n>>m>>P){if(n<m){cout<<0<<endl;continue;}num=0;memset(A,0,sizeof(A));memset(M,0,sizeof(M));for(LL x=P,i=2;i<=P;++i)if(x%i==0){M[++num]=1;while(x%i==0){M[num]*=i;x/=i;}A[num]=exlucas(n,m,i,M[num])%P;} cout<<crt(num,P)<<endl;}return 0;
}
数论-卢卡斯定理(lucas)与拓展卢卡斯定理 (exlucas)相关推荐
- 【luogu P3807】【模板】卢卡斯定理/Lucas 定理(含 Lucas 定理证明)
[模板]卢卡斯定理/Lucas 定理 题目链接:luogu P3807 题目大意 求 C(n,n+m)%p 的值. p 保证是质数. 思路 Lucas 定理内容 对于非负整数 nnn,mmm,质数 p ...
- 牛客练习赛22 E 树状数组 + DFS + 拓展欧几里德定理
题目链接 题意: 给定一个长度为nnn的序列,进行mmm次操作,操作有两类: 111 LLL RRR vvv : 区间[L,R][L, R][L,R]的每个数加上vvv 222 LLL RRR ppp ...
- 欧几里德与拓展欧几里德定理
一.欧几里德定理 欧几里德定理就是辗转相除法的原理,用来求两个整数的最大公约数gcd(a, b). 推理过程: 辗转相除法是由辗转相减法而来的,如果a和b(假设a>b)的最大公约数是k,那么可以 ...
- 初等数论四大定理之——费马小定理
皮埃尔·德·费马(Pierre de Fermat),1601年生于法国,是一个律师和业余数学家.他在数学多个分支上都有贡献,成就甚至超过了许多职业的数学家,被誉为"业余数学家之王" ...
- 初等数论四大定理(威尔逊定理,欧拉定理,中国剩余定理,费马小定理)
1.威尔逊定理:在初等数论中,威尔逊定理给出了判定一个自然数是否为素数的充分必要条件.即:当且仅当p为素数时:( p -1 )! ≡ p-1 ( mod p ),但是由于阶乘是呈爆炸增长的,其结论对于 ...
- donsker定理_中心极限定理和Donsker定理
为什么要关心中心极限定理和Donsker定理 这可能就是Donsker定理要解决的问题.与Donsker定理相关的,还有Glivenko-Cantelli Theorem,似乎与中心极限定理与大数定律 ...
- 【组合数学】组合存在性定理 ( 三个组合存在性定理 | 有限偏序集分解定理 | Ramsey 定理 | 相异代表系存在定理 | Ramsey 定理内容概要 )
文章目录 一.组合存在性定理 二.Ramsey 定理内容概要 一.组合存在性定理 组合存在性定理 主要有三个定理 , 有限偏序集分解定理 , Ramsey 定理 , 相异代表系存在定理 ; 1. 有限 ...
- (组合数学笔记)Pólya计数理论_Part.9_Pólya定理的推广——De Bruijn定理
文章目录 写在前面 问题引入 推导1 定理 推导2 De Bruijn定理 定理的特殊情况 CCC上没有置换群 HHH上没有置换群 C,HC,\,HC,H上均没有置换群 例题 分析 写在前面 总结推广 ...
- 第7讲 替代定理、戴维南定理、诺顿定理
替代定理.戴维南定理.诺顿定理 1.替代定理 2.戴维南定理 3.诺顿定理 4.戴维南定理和诺顿定理的等效 1.替代定理 ●内容: 任何一支路可以用一个独立电压源或独立电流源代替,只要电压源的电压等于 ...
最新文章
- Java 8 - 06 Lambda 和方法引用实战
- Optional 的基本用法
- 54款开源服务器软件(内容管理、数据库、电子商务、邮件服务器、文件传输、操作系统、安全、小公司服务 .
- VS2017中的附加到进程
- 个人应用开发详记. (三)
- 关注微信公众号使其自动发送欢迎你关注消息
- oracle数据库listener开启和关闭trace文件的方法
- 项目开发中XML 读取错误总结
- 费率转换成利率的计算器_存款利率计算器
- 计算机天空之城音乐谱,天谕手游天空之城乐谱代码是什么
- 恶意软件通信协议的应用现状分析
- MuMu模拟器Unity Profiler
- 计算机网络常见面试题整理
- Unrecognized DataType
- npm、cnpm、yarn安装指定版本的依赖包
- P2392 kkksc03考前临时抱佛脚
- Learning to Learn
- Python 用3D引擎写一个Pong游戏
- 微软、思科等企业源代码被黑客在线售卖,打包价100万美元
- scss主题颜色切换
热门文章
- 一道积分不等式的最优估计探索
- linux ifort编译命令,[Linux] icc与ifort编译器
- java转go之初体验(一)
- 报错:“TypeError: Cannot read property ‘0‘ of undefined“的原因
- js中对数组的增删方法:push(),pop(),unshift(),shift(),splice()的用法小结
- 杭州某公司福禄克FLUKE DTX-SFM2单模模块-修复案例
- 语音识别ASR和NLP有什么区别?
- seo优化教程-免费SEO优化详细教程
- TCP FIN_WAIT1状态的实验和验收
- 什么是幻读?以及如何解决幻读?