Lucas定理--组合数取模

Posted emcikem

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Lucas定理--组合数取模相关的知识,希望对你有一定的参考价值。

Lucas定理是用来求 c(n,m) mod p,p为素数的值。

C(n,m)%p = C(n/p,m/p) * C(n%p,m%p)%p 

(Lucas(n,m,p)=C(n \% p,m \% p) imes Lucas(frac{n}{p},frac{m}{p},p))

(inom{n}{m}=frac{n!}{m!(n-m)!})

卢卡斯定理模板

#include <cstdio>
#include <iostream>
#define ll long long
using namespace std;
ll pow(ll a,ll b,ll p){
    ll ans = 1;
    a%=p;
    while(b){
        if(b&1)ans = (ans%p)*(a%p)%p;
        b>>=1;
        a = a*a%p;
    }
    return ans;
}
ll inv(ll x,ll p){//x关于p的逆元,p为素数
    return pow(x,p-2,p);
}
ll C(ll n,ll m,ll p){//求组合数C(n,m)%p
    if(n<m)return 0;
    ll up=1,down=1;//分子分母
    for(ll i=n-m+1;i<=n;i++)up=up*i%p;
    for(ll i=1;i<=m;i++)down=down*i%p;
    return up*inv(down,p)%p;
}
ll lucas(ll n,ll m,ll p){
    if(m==0)return 1;
    return C(n%p,m%p,p)*lucas(n/p,m/p,p)%p;
}
int main(){
    int t;
    cin>>t;
    ll n,m,p;
    while(t--){
        cin>>n>>m>>p;
        cout<<lucas(n,m,p)<<endl;
    }
    return 0;
}

扩展卢卡斯定理

当p不为素数的时候

以上是关于Lucas定理--组合数取模的主要内容,如果未能解决你的问题,请参考以下文章

Lucas定理及组合数取模

组合数取模 (lucas 定理)

组合数取模

组合数取模(Lucas)

组合数取模 Lucas

大组合数取余模板Lucas定理