BZOJ.2142.礼物(扩展Lucas)
答案就是C(n,m1) * C(n-m1,m2) * C(n-m1-m2,m3)...(mod p)
使用扩展Lucas求解。
一个很简单的优化就是把pi,pi^ki次方存下来,因为每次分解p都是很慢的。
注意最后p不为1要把p再存下来!(质数)
COGS 洛谷上的大神写得快到飞起啊QAQ 就这样吧
3.25 Update:预处理阶乘可以很快,别忘longlong。代码见下。
//836kb 288ms
#include <cmath>
#include <cstdio>
typedef long long LL;
int cnt,P[500],PK[500];
LL FP(LL x,int k,LL p)
{
LL t=1ll;
for(; k; k>>=1,x=x*x%p)
if(k&1) t=t*x%p;
return t;
}
LL 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)%p;
}
LL Fact(LL x,LL pi,LL pk)//Calc x! % (pk=pi^ki)(x!中无pi因子)
{
if(!x) return 1ll;
LL res=1ll;
if(x>=pk)
{
for(int i=2; i<pk; ++i)//从1开始没什么用
if(i%pi) (res*=i)%=pk;//无pi因子!
res=FP(res,x/pk,pk);
}
for(int i=2; i<=x%pk; ++i)
if(i%pi) (res*=i)%=pk;
return res*Fact(x/pi,pi,pk)%pk;
}
int C(LL n,LL m,LL pi,LL pk,LL mod)//int
{
if(n<m) return 0;
LL a=Fact(n,pi,pk),b=Fact(m,pi,pk),c=Fact(n-m,pi,pk);int k=0;
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;
LL res=a*Inv(b,pk)%pk*Inv(c,pk)%pk*FP(pi,k,pk)%pk;
return res*(mod/pk)%mod*Inv(mod/pk,pk)%mod;
}
LL Solve(int n,int m,int p)
{
if(!n) return 1ll;
int res=0;
for(int i=1; i<=cnt; ++i) (res+=C(n,m,P[i],PK[i],p))%=p;
return (LL)res;
}
int main()
{
int n,m,p,t[9];
scanf("%d%d%d",&p,&n,&m);
int sum=0;
for(int i=1; i<=m; ++i) scanf("%d",&t[i]),sum+=t[i];
if(sum>n) {puts("Impossible"); return 0;}
int now=p;
for(int i=2,lim=sqrt(p+0.5); i<=lim; ++i)
if(!(now%i))
{
int pk=1;
while(!(now%i)) now/=i,pk*=i;
P[++cnt]=i, PK[cnt]=pk;
if(now==1) break;
}
if(now!=1) P[++cnt]=now,PK[cnt]=now;
LL res=1ll;
for(int i=1; i<=m; ++i) (res*=Solve(n,t[i],p))%=p,n-=t[i];
printf("%lld",res);
return 0;
}
Update:
/*
1620kb 184ms
不预处理:836kb 288ms
答案就是C(n,m1)*C(n-m1,m2)*C(n-m1-m2,m3)...使用扩展Lucas求解。
一个很简单的优化就是把pi,pi^ki次方存下来,因为每次分解p都是很慢的。
注意最后p不为1要把p再存下来!(质数)
预处理阶乘。不想麻烦就开longlong。
*/
#include <cmath>
#include <cstdio>
typedef long long LL;
int cnt,P[500],PK[500];
LL fac[100005];//开longlong!
LL FP(LL x,int k,LL p)
{
LL t=1ll;
for(; k; k>>=1,x=x*x%p)
if(k&1) t=t*x%p;
return t;
}
LL 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)%p;
}
LL Fact(LL x,LL pi,LL pk)//Calc x! % (pk=pi^ki)(x!中无pi因子)
{
if(!x) return 1ll;
LL res=1ll;
if(x>=pk) res=FP(fac[pk],x/pk,pk);
res=res*fac[x%pk]%pk;
return res*Fact(x/pi,pi,pk)%pk;
}
int C(LL n,LL m,LL pi,LL pk,LL mod)//int
{
if(n<m) return 0;
fac[0]=1;
for(int i=1; i<=pk; ++i)
if(i%pi) fac[i]=1ll*fac[i-1]*i%pk;
else fac[i]=fac[i-1];
LL a=Fact(n,pi,pk),b=Fact(m,pi,pk),c=Fact(n-m,pi,pk);int k=0;
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;
LL res=a*Inv(b,pk)%pk*Inv(c,pk)%pk*FP(pi,k,pk)%pk;
return res*(mod/pk)%mod*Inv(mod/pk,pk)%mod;
}
LL Solve(int n,int m,int p)
{
if(!n) return 1ll;
int res=0;
for(int i=1; i<=cnt; ++i) (res+=C(n,m,P[i],PK[i],p))%=p;
return (LL)res;
}
int main()
{
int n,m,p,t[9];
scanf("%d%d%d",&p,&n,&m);
int sum=0;
for(int i=1; i<=m; ++i) scanf("%d",&t[i]),sum+=t[i];
if(sum>n) {puts("Impossible"); return 0;}
int now=p;
for(int i=2,lim=sqrt(p+0.5); i<=lim; ++i)
if(!(now%i))
{
int pk=1;
while(!(now%i)) now/=i,pk*=i;
P[++cnt]=i, PK[cnt]=pk;
if(now==1) break;
}
if(now!=1) P[++cnt]=now,PK[cnt]=now;
LL res=1ll;
for(int i=1; i<=m; ++i) (res*=Solve(n,t[i],p))%=p,n-=t[i];
printf("%lld",res);
return 0;
}
BZOJ.2142.礼物(扩展Lucas)的更多相关文章
- bzoj 2142 礼物——扩展lucas模板
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2142 没给P的范围,但说 pi ^ ci<=1e5,一看就是扩展lucas. 学习材料 ...
- BZOJ - 2142 礼物 (扩展Lucas定理)
扩展Lucas定理模板题(貌似这玩意也只能出模板题了吧~~本菜鸡见识鄙薄,有待指正) 原理: https://blog.csdn.net/hqddm1253679098/article/details ...
- BZOJ 2142: 礼物 [Lucas定理]
2142: 礼物 Time Limit: 10 Sec Memory Limit: 259 MBSubmit: 1294 Solved: 534[Submit][Status][Discuss] ...
- [BZOJ2142]礼物(扩展Lucas)
2142: 礼物 Time Limit: 10 Sec Memory Limit: 259 MBSubmit: 2286 Solved: 1009[Submit][Status][Discuss] ...
- BZOJ 2142 礼物 组合数学 CRT 中国剩余定理
2142: 礼物 Time Limit: 10 Sec Memory Limit: 259 MBSubmit: 1450 Solved: 593[Submit][Status][Discuss] ...
- 【刷题】BZOJ 2142 礼物
Description 一年一度的圣诞节快要来到了.每年的圣诞节小E都会收到许多礼物,当然他也会送出许多礼物.不同的人物在小E 心目中的重要性不同,在小E心中分量越重的人,收到的礼物会越多.小E从商店 ...
- [bzoj2142]礼物(扩展lucas定理+中国剩余定理)
题意:n件礼物,送给m个人,每人的礼物数确定,求方案数. 解题关键:由于模数不是质数,所以由唯一分解定理, $\bmod = p_1^{{k_1}}p_2^{{k_2}}......p_s^{{k_ ...
- BZOJ2142 礼物 扩展lucas 快速幂 数论
原文链接http://www.cnblogs.com/zhouzhendong/p/8110015.html 题目传送门 - BZOJ2142 题意概括 小E购买了n件礼物,送给m个人,送给第i个人礼 ...
- BZOJ 2142 礼物 数论
这道题是求组合数终极版. C(n,m) mod P n>=1e9 m>=1e9 P>=1e9且为合数且piqi<=1e5 拓展lucas定理. 实际上就是一点数论小知识的应用. ...
随机推荐
- 机器学习:分类算法性能指标之ROC曲线
在介绍ROC曲线之前,先说说混淆矩阵及两个公式,因为这是ROC曲线计算的基础. 1.混淆矩阵的例子(是否点击广告): 说明: TP:预测的结果跟实际结果一致,都点击了广告. FP:预测结果点击了,但是 ...
- github 远程仓库
因为本地Git仓库和GitHub仓库之间的传输是通过SSH加密的,所以设置一下 第1步:创建SSH Key.在用户主目录下,看看有没有.ssh目录,如果有,再看看这个目录下有没有id_rsa和id_r ...
- 用Emacs将文件加密保存
为Emacs安装ps-ccrypt插件. 如果你在使用elpa(Emacs的一个插件管理器), 可以M-x list-packages, 从插件列表中找到 ps-ccrypt, 在该项上按i将其标记为 ...
- idea-plugin
codehelper.generator https://github.com/zhengjunbase/codehelper.generator?id=5f5b0005-11fb-48e4-bdb7 ...
- linux系统时间不同步解决办法(同步本地时间)
改变/etc/目录下的localtime文件,既可以改变当前的时区 1.方法是到/usr/share/zoneinfo目录下找到你要相对应的时区文件,例如上海在/usr/share/zoneinfo/ ...
- 【Hadoop】搭建完全分布式的hadoop【转】
转自:http://www.cnblogs.com/laov/p/3421479.html 下面博文已更新,请移步 ↑ 用于测试,我用4台虚拟机搭建成了hadoop结构 我用了两个台式机.一个xp系统 ...
- Linux监控重要进程的实现方法
Linux监控重要进程的实现方法 不管后台服务程序写的多么健壮,还是可能会出现core dump等程序异常退出的情况,但是一般情况下需要在无 人为干预情况下,能够自动重新启动,保证服务进程能够服务用户 ...
- 巧用PHP数组函数
2014年3月5日 08:48:39 情景:项目中需要根据传递来的参数的不同,使用不同的缓存 假如传递来的参数最多有这几个(在这个范围内,但是每次传过来的参数不确定): $arg = array( ' ...
- 如何动态修改windows下的host文件
事件背景:为了测试数据提交后,需要在另一个环境的多个测试节点下去验证测试数据是否添加成功,找了一大堆放法,用了比较笨的方法实现了.不多废话思路如下: 为了万无一失,先备份hosts文件内容: 1.读取 ...
- Demo005 小学四则运算自动生成程序
目录 小学四则运算自动生成程序 0.传送门 1.题目要求 2.功能实现 2.1 总体设计 2.2 用户欢迎界面 2.3 用户功能界面 2.4 屏幕输出 2.5 文本输出 2.6 获取时间 2.7 用户 ...