【NOI P模拟赛】大阶乘(斯特林数)
题意
求
16
16
16 进制下,
n
!
n!
n! 去掉尾部
0
0
0 后取模
2
64
2^{64}
264 的结果。
n
<
2
64
n<2^{64}
n<264
一共
T
≤
10
T\leq10
T≤10 组数据。
题解
存在一个末尾的
0
0
0 ,意味着能被
2
4
2^4
24 整除。我们就把这个数含有的
2
2
2 的次数求出来,取模
4
4
4 ,再乘上去。我们可以用扩展Lucas类似的方法,把目标不断除以 2 来统计,即依次统计能被
2
1
,
2
2
,
2
3
,
.
.
.
,
2
63
2^1,2^2,2^3,...,2^{63}
21,22,23,...,263 整除的数的个数,再加起来。剔除所有的
2
2
2 后,答案变成了
∏
i
=
0
f
(
n
2
i
)
\prod_{i=0} f(\frac{n}{2^i})
i=0∏f(2in)
其中
f
(
n
)
=
∏
i
=
1
(
n
+
1
)
/
2
−
1
(
2
i
+
1
)
f(n)=\prod_{i=1}^{(n+1)/2-1}(2i+1)
f(n)=∏i=1(n+1)/2−1(2i+1) 。
现在我们的问题变成了求
f
(
n
)
f(n)
f(n) ,我们把它展开,
喔
唷
,
崩
溃
啦
_{喔\,唷,\,崩\,溃\,啦}
喔唷,崩溃啦
这里的
n
n
n 太大了,看来我们得换个思路,我们令
2
=
x
2=x
2=x ,在取模
2
64
2^{64}
264 下,我们会发现只存在
x
x
x 的
1
∼
63
1\sim63
1∼63 次项。我们再展开:
∑
i
=
0
63
g
(
n
+
1
2
−
1
,
i
)
⋅
x
i
\sum_{i=0}^{63} g(\frac{n+1}{2}-1,i)\cdot x^i
i=0∑63g(2n+1−1,i)⋅xi
这里的
g
(
n
,
m
)
g(n,m)
g(n,m) 表示从
1
∼
n
1\sim n
1∼n 中选
m
m
m 个数相乘的所有方案之和。
未曾设想的方向:
g
(
n
,
m
)
g(n,m)
g(n,m) 是可以递推的,不难得出递推式为
g
(
n
,
m
)
=
g
(
n
−
1
,
m
)
+
g
(
n
−
1
,
m
−
1
)
×
n
g(n,m)=g(n-1,m)+g(n-1,m-1)\times n
g(n,m)=g(n−1,m)+g(n−1,m−1)×n
这个式子看起来有点熟悉,我们想想另一个递推式:
s
(
n
,
m
)
=
s
(
n
−
1
,
m
−
1
)
+
s
(
n
−
1
,
m
)
×
(
n
−
1
)
s(n,m)=s(n-1,m-1)+s(n-1,m)\times(n-1)
s(n,m)=s(n−1,m−1)+s(n−1,m)×(n−1)
所以不难发现第一类斯特林数
s
(
n
,
m
)
s(n,m)
s(n,m) 和
g
(
n
,
m
)
g(n,m)
g(n,m) 之间的关系:
g
(
n
,
m
)
=
s
(
n
+
1
,
n
−
m
+
1
)
g(n,m)=s(n+1,n-m+1)
g(n,m)=s(n+1,n−m+1)
太好啦,我们可以直接计算第一类斯特林数:
喔
唷
,
崩
溃
啦
_{喔\,唷,\,崩\,溃\,啦}
喔唷,崩溃啦
还是不行,因为这里的
n
+
1
n+1
n+1 太大了,
m
m
m 虽然很小,但是
n
−
m
+
1
n-m+1
n−m+1 太大了。
考虑到第一类斯特林数的定义是若干个数组成圆排列,我们可以利用
m
m
m ,因为大小超过
1
1
1 的圆排列个数小于等于
m
m
m 。所以:
s
(
n
+
1
,
n
−
m
+
1
)
=
∑
i
=
0
m
d
p
[
m
]
[
i
]
⋅
(
n
+
1
m
+
i
)
s(n+1,n-m+1)=\sum_{i=0}^{m} dp[m][i]\cdot{n+1\choose m+i}
s(n+1,n−m+1)=i=0∑mdp[m][i]⋅(m+in+1)
其中
d
p
[
i
]
[
j
]
dp[i][j]
dp[i][j] 表示
i
+
j
i+j
i+j 个数形成
j
j
j 个大小不为
1
1
1 的圆排列的方案数,
这个也是可以递推的,讨论最末尾一个圆排列大小是否大于
2
2
2 ,可得递推式
d
p
[
i
]
[
j
]
=
(
d
p
[
i
−
1
]
[
j
]
+
d
p
[
i
−
1
]
[
j
−
1
]
)
×
(
i
+
j
−
1
)
dp[i][j]=\big(dp[i-1][j] + dp[i-1][j-1]\big)\times\big(i+j-1\big)
dp[i][j]=(dp[i−1][j]+dp[i−1][j−1])×(i+j−1)
组合数的计算是个难题,因为要用除法,但是
2
64
2^{64}
264 又不是个很好的模数。
所以,我们要把分子和分母的所有
2
2
2 都提出来,然后相除,再放到组合数里。
综合算下来,时间复杂度
O
(
T
log
4
n
)
O(T\log^4n)
O(Tlog4n),可过。
CODE
#include<set>
#include<map>
#include<queue>
#include<stack>
#include<random>
#include<vector>
#include<bitset>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define MAXN 10000005
#define LL long long
#define ULL unsigned long long
#define DB double
#define lowbit(x) (-(x) & (x))
#define ENDL putchar('\n')
#define FI first
#define SE second
LL read() {
LL f=1,x=0;int s = getchar();
while(s < '0' || s > '9') {if(s<0)return -1;if(s=='-')f=-f;s = getchar();}
while(s >= '0' && s <= '9') {x = (x<<3) + (x<<1) + (s^48); s = getchar();}
return f*x;
}
const char sxt[16] = {'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
ULL readull() {
ULL x=0;int s = getchar();
while(s < '0' || s > '9') {if(s < 0) return 0;s = getchar();}
while(s >= '0' && s <= '9') {x=(x<<3)+(x<<1)+(s^48); s = getchar();}
return x;
}
void putpos(ULL x) {if(!x)return ;putpos(x>>4);putchar(sxt[x&15]);}
void putnum(ULL x) {
if(!x) {putchar('0');return ;}
return putpos(x);
}
void AIput(ULL x,int c) {putnum(x);putchar(c);}
int n,m,s,o,k;
ULL inv[128];
ULL facf(ULL x) {
if(!x) return 1ull;
ULL dp[128][128] = {};
dp[0][0] = 1;
for(int i = 1;i <= 126 && i <= x;i ++) {
for(int j = 1;j <= i;j ++) {
dp[i][j] = dp[i-1][j] * (i-1+j) + dp[i-1][j-1] * (i-1+j);
}
}
if(!(x&1)) x --;
ULL n = x/2 + 1;
ULL ans = 0,pw = 1;
for(int i = 0;i <= 63 && i <= n;i ++,pw <<= 1) {
ULL stl = 0;
ULL c1[128],c2 = 1,tlc2 = 1;
for(int j = 1;j <= i*2 && j <= n;j ++) {
c1[j] = n-j+1;
int b = j,cn = 0;
while(!(b&1)) b>>=1,cn++;
for(int k = 1;k <= j && cn;k ++) {
while(cn && !(c1[k]&1)) c1[k]>>=1,cn --;
}
c2 *= inv[b];
tlc2 *= b;
if(j > i) {
ULL C = c2;
for(int k = 1;k <= j;k ++) C *= c1[k];
stl += C * dp[i][j-i];
}
}
if(i == 0) stl = 1;
ans += pw * stl;
}
return ans;
}
int main() {
freopen("multiplication.in","r",stdin);
freopen("multiplication.out","w",stdout);
inv[0] = 1;
for(int i = 1;i <= 128;i += 2) {
ULL a = i;
inv[i] = i;
for(int j = 1;j <= 62;j ++) {
a = a * a;
inv[i] *= a;
}
}
int T = read();
while(T --) {
ULL N = readull();
int ct = 0;
ULL b = 1,as = facf(N);
for(int i = 1;i < 64;i ++) {
b <<= 1;
ct += (N/b) & 3;
ct &= 3;
as *= facf(N/b);
}
for(int i = 1;i <= ct;i ++) as *= 2ull;
AIput(as,'\n');
}
return 0;
}
【NOI P模拟赛】大阶乘(斯特林数)的更多相关文章
- hdu 4045 2011北京赛区网络赛F 组合数+斯特林数 ***
插板法基础知识 斯特林数见百科 #include<iostream> #include<cmath> #include<cstdio> #include<cs ...
- 【NOI P模拟赛】(要素过多的标题)(容斥原理)
题面 0 题目背景 [ 数 据 删 除 ] _{^{[数\,据\,删\,除]}} [数据删除] 1 题目描述 在执行任务时,收集到了 n n n 份能源,其中第 i i i 份的能量值是 ...
- [NOI P模拟赛] 传统艺能(子序列自动机、矩阵乘法,线段树)
(2:00)OID:"完了,蓝屏了!"(代码全消失) 众人欢呼 OID:开机,"原题测试--" (30min later)OID 开始传统艺能: " ...
- [NOIP2018校模拟赛]T1 阶乘
题目: 描述 有n个正整数a[i],设它们乘积为p,你可以给p乘上一个正整数q,使p*q刚好为正整数m的阶乘,求m的最小值. 输入 共两行. 第一行一个正整数n. 第二行n个正整数a[i]. 输出 共 ...
- 【XJOI】【NOI考前模拟赛7】
DP+卡常数+高精度/ 计算几何+二分+判区间交/ 凸包 首先感谢徐老师的慷慨,让蒟蒻有幸膜拜了学军的神题.祝NOI2015圆满成功 同时膜拜碾压了蒟蒻的众神QAQ 填填填 我的DP比较逗比……( ...
- noip模拟赛 大芳的逆行板载
题目背景 大芳有一个不太好的习惯:在车里养青蛙.青蛙在一个n厘米(11n毫米s)的Van♂杆子上跳来跳去.她时常盯着青蛙看,以至于突然逆行不得不开始躲交叉弹.有一天他突发奇想,在杆子上每1厘米为一个单 ...
- NOI.ac模拟赛20181021 ball sequence color
T1 ball 可以发现每次推动球时,是将每个球的位置 −1-1−1 ,然后把最左边的球放到 P−1P-1P−1 处. 记个 −1-1−1 次数,再用set维护就好了. #include <bi ...
- 【NOI P模拟赛】最短路(树形DP,树的直径)
题面 给定一棵 n n n 个结点的无根树,每条边的边权均为 1 1 1 . 树上标记有 m m m 个互不相同的关键点,小 A \tt A A 会在这 m m m 个点中等概率随机地选择 k k k ...
- noi.acNOIP模拟赛5-count
题目链接 戳我 题意简述 你有一个n+1个数的序列,都是1~n,其中只有一个有重复,求每个长度的本质不同的子序列个数.\(mod 1e9+7\). sol 说起来也很简单,设相同的数出现的位置为\(l ...
随机推荐
- NB-IoT/LoRa/eMTC和蓝牙/WiFi的关系是互补还是替代?
近年来,相继出现了许多物联网技术.WiFi.蓝牙.NB-IoT.LoRa.eMTC和其他技术为IoT实践提供了一流的技术支持通讯端口.拥有这么多技术,能够互相替代吗?还是能起到互补的作用?为低功耗广域 ...
- Docker容器安装RabbitMQ
Docker容器安装RabbitMQ 准备资料 erlang的rpm安装包 https://github.com/rabbitmq/erlang-rpm/releases rabbitmq的rpm安装 ...
- c# sqlsugar,hisql,freesql orm框架全方位性能测试对比 sqlserver 性能测试
在2022年1月份本人做过一次sqlsugar,hisql,freesql三个框架的性能测试,上次主要是测的sqlserver下的常规插入(非bulkcopy的方式数据插入),hisql与目前比较流行 ...
- Operator介绍
一.Operator简介 在Kubernetes中我们经常使用Deployment.DaemonSet.Service.ConfigMap等资源,这些资源都是Kubernetes的内置资源,他们的创建 ...
- jQuery获取市、区县、乡镇、村
效果图: 首先根据自己方法把地区树状结构json字符串拿到 html下拉框和js写法如下: <select class="form-control" style=" ...
- MySql查看索引以及各字段含义
查看表的索引: show index from userInfo(表名) show index from 数据库名.表名 查看某表某一列上的索引使用下面的SQL语句: show index from ...
- mongodb 数据块迁移的源码分析
1. 简介 上一篇我们聊到了mongodb数据块的基本概念,和数据块迁移的主要流程,这篇文章我们聊聊源码实现部分. 2. 迁移序列图 数据块迁移的请求是从配置服务器(config server)发给( ...
- 关于Thymeleaf无法取值问题
SpringBoot2.7以前的版本在获取model中数据的时候不需要注释,2.7以后的版本需要加注释,它无法直接取存在model中的数据,不加注释的时候会爆红但是可以正常使用,这个注释的含义就是指定 ...
- 时间模块之datatime模块、os模块、sys模块、json模块、json模块实操
目录 一.模块的绝对导入和相对导入 二.包的概念 三.编程思想的转变 四.软件开发目录规范 五.常见的内置模块 一.时间模块之datatime模块 1.datetime.datetime.today( ...
- Solution -「基环树」做题记录
写的大多只是思路,比较简单的细节和证明过程就不放了,有需者自取. 基环树简介 简单说一说基环树吧.由名字扩展可得这是一类以环为基础的树(当然显然它不是树. 通常的表现形式是一棵树再加一条非树边,把图画 ...