数论——lucas定理

网上证明很多,虽然没看懂。。。。

主要解决大组合数取模的情况

百度之星2016 1003

先推公式,再lucas

p很大的情况 1e9+7

 1 #include<iostream>
 2 #include<string>
 3 #include<algorithm>
 4 #include<cstdlib>
 5 #include<cstdio>
 6 #include<set>
 7 #include<map>
 8 #include<vector>
 9 #include<cstring>
10 #include<stack>
11 #include<cmath>
12 #include<queue>
13 #define clc(a,b) memset(a,b,sizeof(a))
14 #include <bits/stdc++.h>
15 const int maxn = 20005;
16 const int inf=0x3f3f3f3f;
17 const double pi=acos(-1);
18 typedef long long LL;
19 using namespace std;
20 const LL MOD = 1e9+7;
21
22 LL exp_mod(LL a, LL b, LL p)
23 {
24     LL res = 1;
25     while(b != 0)
26     {
27         if(b&1) res = (res * a) % p;
28         a = (a*a) % p;
29         b >>= 1;
30     }
31     return res;
32 }
33
34 LL Comb(LL a, LL b, LL p)
35 {
36     if(a < b)   return 0;
37     if(a == b)  return 1;
38     if(b > a - b)   b = a - b;
39
40     LL ans = 1, ca = 1, cb = 1;
41     for(LL i = 0; i < b; ++i)
42     {
43         ca = (ca * (a - i))%p;
44         cb = (cb * (b - i))%p;
45     }
46     ans = (ca*exp_mod(cb, p - 2, p)) % p;
47     return ans;
48 }
49
50 LL Lucas(int n, int m, int p)
51 {
52     LL ans = 1;
53
54     while(n&&m&&ans)
55     {
56         ans = (ans*Comb(n%p, m%p, p)) % p;
57         n /= p;
58         m /= p;
59     }
60     return ans;
61 }
62
63 int main()
64 {
65     int n, m;
66     LL p;
67     while(~scanf("%d%d", &n, &m))
68     {
69         p=MOD;
70         printf("%I64d\n", Lucas(n+m-4, m-2, p));
71     }
72     return 0;
73 }

p在100000左右

HDU 3037

 1 #include<iostream>
 2 #include<string>
 3 #include<algorithm>
 4 #include<cstdlib>
 5 #include<cstdio>
 6 #include<set>
 7 #include<map>
 8 #include<vector>
 9 #include<cstring>
10 #include<stack>
11 #include<cmath>
12 #include<queue>
13 #define clc(a,b) memset(a,b,sizeof(a))
14 #include <bits/stdc++.h>
15 const int maxn = 20005;
16 const int inf=0x3f3f3f3f;
17 const double pi=acos(-1);
18 typedef long long LL;
19 using namespace std;
20 //const LL MOD = 1e9+7;
21
22 LL PowMod(LL a,LL b,LL MOD){
23     LL ret=1;
24     while(b){
25         if(b&1) ret=(ret*a)%MOD;
26         a=(a*a)%MOD;
27         b>>=1;
28     }
29     return ret;
30 }
31 LL fac[100005];
32 LL Get_Fact(LL p){
33     fac[0]=1;
34     for(int i=1;i<=p;i++)
35         fac[i]=(fac[i-1]*i)%p;
36 }
37 LL Lucas(LL n,LL m,LL p){
38     LL ret=1;
39     while(n&&m){
40         LL a=n%p,b=m%p;
41         if(a<b) return 0;
42         ret=(ret*fac[a]*PowMod(fac[b]*fac[a-b]%p,p-2,p))%p;
43         n/=p;
44         m/=p;
45     }
46     return ret;
47 }
48 int main(){
49     int t;
50     scanf("%d",&t);
51     while(t--){
52         LL n,m,p;
53         scanf("%I64d%I64d%I64d",&n,&m,&p);
54         Get_Fact(p);
55         printf("%I64d\n",Lucas(n+m,m,p));
56     }
57     return 0;
58 }
时间: 2024-11-10 01:16:48

数论——lucas定理的相关文章

CPC23-4-K. 喵喵的神数 (数论 Lucas定理)

喵喵的神?数 Time Limit: 1 Sec Memory Limit: 128 MB Description 喵喵对组合数比較感兴趣,而且对计算组合数很在行. 同一时候为了追求有后宫的素养的生活,喵喵每天都要研究 质数. 我们先来复习一下什么叫做组合数.对于正整数P.T 然后我们再来复习一下什么叫质数.质数就是素数,假设说正整数N的约数仅仅有1和它本身,N就是质数:另外. 1不是质数. 今天,喵喵想要知道 Input 输入第一行是一个整数N(N<=1000). 接下来N行,每行包含一个正整

数论(Lucas定理) HDOJ 4349 Xiao Ming&#39;s Hope

题目传送门 题意:求C (n,0),C (n,1),C (n,2)...C (n,n)中奇数的个数 分析:Lucas 定理:A.B是非负整数,p是质数.AB写成p进制:A=a[n]a[n-1]...a[0],B=b[n]b[n-1]...b[0].则组合数C(A,B)与C(a[n],b[n])*C(a[n-1],b[n-1])*...*C(a[0],b[0])  mod p同.即:Lucas (n,m,p)=C (n%p,m%p) * Lucas (n/p,m/p,p)  我是打表找规律的,就是

Bzoj 4591: [Shoi2015]超能粒子炮&#183;改 数论,Lucas定理,排列组合

4591: [Shoi2015]超能粒子炮·改 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 178  Solved: 70[Submit][Status][Discuss] Description 曾经发明了脑洞治疗仪&超能粒子炮的发明家SHTSC又公开了他的新发明:超能粒子炮·改--一种可以发射威力更加 强大的粒子流的神秘装置.超能粒子炮·改相比超能粒子炮,在威力上有了本质的提升.它有三个参数n,k.它会 向编号为0到k的位置发射威力为C(n

BZOJ 1951 SDOI2010 古代猪文 数论 Lucas定理

题目大意:给定N,G,求 首先由欧拉定理易知当A与p互质时A^B %p=A^(B%φ(p) ) %p 这里p是一个质数 于是φ(p)=p-1=999911658 然后由于这个数不是质数 难以处理 我们将它分解质因数 然后对于每个质因数的解用中国剩余定理合并即可 然后就是999911658有一个很好的性质 999911658=2*3*4679*35617 每个质因数的次数都是1次 于是我们可以套用卢卡斯定理 预先处理出对于每个质因数的阶乘和阶乘的逆元即可 注意此题有个细节 就是欧拉定理中a与p必须

【学习总结】数学-lucas定理

定义: 数论Lucas定理是用来求 C(mn)%p的值, p是素数. 描述: lucas(n,m,p)=lucas(n/p,m/p,p)?C(m%pn%p) lucas(n,0,p)=1 证明: 设p为素数,A,B为正整数,并且有(即A,B的p进制情况): A=akpk+ak?1pk?1+-+a1p1+a0 B=bkpk+bk?1pk?1+-+b1p1+b0 因为C(jp)=C(j?1p?1)?pj=0 (含有因子p) 所以(1+x)t(modp)=(1+xt)(modp) (中间展开项均含有C

HDU 3037 Saving Beans (数论,Lucas定理)

题意:问用不超过 m 颗种子放到 n 棵树中,有多少种方法. 析:题意可以转化为 x1 + x2 + .. + xn = m,有多少种解,然后运用组合的知识就能得到答案就是 C(n+m, m). 然后就求这个值,直接求肯定不好求,所以我们可以运用Lucas定理,来分解这个组合数,也就是Lucas(n,m,p)=C(n%p,m%p)* Lucas(n/p,m/p,p). 然后再根据费马小定理就能做了. 代码如下: 第一种: #pragma comment(linker, "/STACK:10240

Lucas定理 中国剩余定理 数论

逆元: 若 a*b=1(%p) 则a是b在%p意义下的逆元.  则在%p意义下  一个数 除以a就等价于乘b 两种求逆元方法:1.若p为质数时,则有性质则a^(p-1)=1(%p) .   即a*a^(p-2)=1(%p).   所以a的逆元就是a^(p-2)  2.exgcd(a,b,x,y) 可求 ax+by=c=gcd(a,b)  若a,b互质 则可求a%b下的逆元 Lucas定理:{ 求C(n,m)在%p下的值    (p是质数)    -- Lucas(n,m,p)=c(n%p,m%p

学习:Lucas定理

模板题 Lucas定理 在数论中,Lucas定理用于计算二项式系数\({\tbinom {m}{n}}\)被质数\(p\)除的所得的余数. 描述 设\(p\)为素数,\(a,b\in N_+\),且 \[a=a_kp^k+a_{k-1}p^{k-1}+\cdots+a_1p+a_0\] \[b=b_kp^k+b_{k-1}p^{k-1}+\cdots+b_1p+b_0\] 这里\(0\leq a_i,b_i\leq p-1\bigwedge a_i,b_i\in Z(i=0,1,2,3,\cdo

BZOJ 4403 2982 Lucas定理模板

思路: Lucas定理的模板题.. 4403 //By SiriusRen #include <cstdio> using namespace std; const int mod=1000003; #define int long long int cases,N,L,R,fac[mod],inv[mod]; int C(int n,int m){ if(n<m)return 0; if(n<mod&&m<mod)return fac[n]*inv[n-m]