出处0.0
用到第二类斯特林数的性质,做法好像很多,我打的是直接ntt,由第二类斯特林数的容斥公式可以推出,我们可以对于每一个i,来一次ntt求出他与所有j组成的第二类斯特林数的值,这个时候我们是O(n^2logn)的,还不如暴力,但是我们发现,对于刚刚提到的容斥的式子,将其化为卷积形式后,其一边的每一项对于每一个i都相同,另一边的每一项是对于所有的i形成一个n项的等比数列,这样我们可以把成等比数列的一边求和,用固定的一边去卷他们的和,这时候的答案的每一项就是所有的i的这一项的和,然后我们再O(n)乘上阶乘和2的次幂就可以了.
(一开始代码打错了,还以为那个公式在S(i,j)不存在的时候是错的……后来手玩了一下才发现他是对的……)
补充:
又用多项式求逆打了一遍,比上面那个做法慢了一倍……
这道题求逆的具体做法参见http://blog.csdn.net/lych_cys/article/details/51512278
感觉好神奇啊,把多项式当成数来推式子……
这个东西感觉有点像CDQ+ntt……

#include <cstdio>
#include <cstring>
#include <algorithm>
const int N=;
const int P=;
typedef long long LL;
inline int Pow(int x,int y){
int ret=;
while(y){
if(y&)ret=(LL)ret*x%P;
x=(LL)x*x%P,y>>=;
}return ret;
}
int A[N],B[N],rev[N],len;
int ai[N],bi[N],ci[N];
int jie[N],ni[N],inv[N],n;
inline void ntt(int *C,int opt){
register int i,j,k,w;int wn,temp;
for(i=;i<len;++i)if(i<rev[i])std::swap(C[i],C[rev[i]]);
for(k=;k<=len;k<<=){
wn=Pow(,(P-)/k);
if(opt==-)wn=Pow(wn,P-);
for(i=;i<len;i+=k){
w=;
for(j=;j<(k>>);++j,w=(LL)w*wn%P){
temp=(LL)w*C[i+j+(k>>)]%P;
C[i+j+(k>>)]=(C[i+j]-temp+P)%P;
C[i+j]=(C[i+j]+temp)%P;
}
}
}
}
inline void mul(int *a,int *b,int *c,int n){
len=;while(len<n)len<<=;int i;
for(i=;i<len;++i)rev[i]=(rev[i>>]>>)|((i&)?(len>>):);
for(i=;i<len;++i)A[i]=a[i],B[i]=b[i];
ntt(A,),ntt(B,);
for(i=;i<len;++i)A[i]=(LL)A[i]*B[i]%P;
ntt(A,-);
int Inv=Pow(len,P-);
for(i=;i<len;++i)c[i]=(LL)A[i]*Inv%P;
}
int main(){
scanf("%d",&n);int i,ans=,temp=;
jie[]=ni[]=,inv[]=;
for(i=;i<=n;++i)inv[i]=((-(LL)(P/i)*inv[P%i])%P+P)%P;
for(i=;i<=n;++i)jie[i]=(LL)jie[i-]*i%P,ni[i]=(LL)ni[i-]*inv[i]%P;
bi[]=,bi[]=n,ai[]=,ai[]=P-;
for(i=;i<=n;++i)
bi[i]=(LL)i*(Pow(i,n)-+P)%P*ni[i]%P*inv[i-]%P,ai[i]=(i&)?(P-ni[i]):ni[i];
mul(ai,bi,ci,n+n+);
for(i=;i<=n;++i)
temp=(((LL)temp)<<1LL)%P,ans=(ans+(LL)ci[i]*temp%P*jie[i])%P;
printf("%d\n",ans);
return ;
}

直接ntt

#include <cstdio>
#include <cstring>
#include <algorithm>
typedef long long LL;
const int N=;
const int P=;
inline int Pow(int x,int y){
int ret=;
while(y){
if(y&)ret=(LL)ret*x%P;
x=(LL)x*x%P,y>>=;
}return ret;
}
int len,n,A[N<<],rev[N<<];
int g[N<<],f[N<<],jie[N],ni[N];
inline void ntt(int *C,int opt){
register int i,j,k,w;int wn,temp;
for(i=;i<len;++i)if(rev[i]>i)std::swap(C[i],C[rev[i]]);
for(k=;k<=len;k<<=){
wn=Pow(,(P-)/k);
if(opt==-)wn=Pow(wn,P-);
for(i=;i<len;i+=k){
w=;
for(j=;j<(k>>);++j,w=(LL)w*wn%P){
temp=(LL)w*C[i+j+(k>>)]%P;
C[i+j+(k>>)]=(C[i+j]-temp+P)%P;
C[i+j]=(C[i+j]+temp)%P;
}
}
}
}
inline void Inv(int *a,int *b,int cd){
if(cd==){b[]=Pow(a[],P-);return;}
Inv(a,b,cd>>);
int i,inv;len=cd<<;
for(i=;i<len;++i)rev[i]=(rev[i>>]>>)|((i&)?(len>>):);
memcpy(A,a,cd<<),memset(A+cd,,cd<<);
ntt(A,),ntt(b,);
for(i=;i<len;++i)b[i]=(-(LL)A[i]*b[i]%P+P)*b[i]%P;
ntt(b,-),inv=Pow(len,P-);
for(i=;i<cd;++i)b[i]=(LL)b[i]*inv%P;
memset(b+cd,,cd<<);
}
int main(){
scanf("%d",&n);int i,cd,ans=;
jie[]=ni[]=;
for(i=;i<=n;++i)jie[i]=(LL)jie[i-]*i%P;
ni[n]=Pow(jie[n],P-);
for(i=n-;i>;--i)ni[i]=(LL)ni[i+]*(i+)%P;
g[]=;
for(i=;i<=n;++i)g[i]=(-*ni[i]+P+P)%P;
cd=;
while(cd<=n)cd<<=;
Inv(g,f,cd);
for(i=;i<=n;++i)ans=(ans+(LL)f[i]*jie[i])%P;
printf("%d\n",ans);
return ;
}

多项式求逆

【BZOJ 4555】[Tjoi2016&Heoi2016]求和 多项式求逆/NTT+第二类斯特林数的更多相关文章

  1. BZOJ 4555: [Tjoi2016&Heoi2016]求和 [分治FFT 组合计数 | 多项式求逆]

    4555: [Tjoi2016&Heoi2016]求和 题意:求\[ \sum_{i=0}^n \sum_{j=0}^i S(i,j)\cdot 2^j\cdot j! \\ S是第二类斯特林 ...

  2. BZOJ 4555 [Tjoi2016&Heoi2016]求和 (多项式求逆)

    题目链接: https://www.lydsy.com/JudgeOnline/problem.php?id=4555 题目大意: 给定 \(S(n,m)\) 表示第二类斯特林数,定义函数 \(f(n ...

  3. bzoj 4555 [Tjoi2016&Heoi2016]求和 NTT 第二类斯特林数 等比数列求和优化

    [Tjoi2016&Heoi2016]求和 Time Limit: 40 Sec  Memory Limit: 128 MBSubmit: 679  Solved: 534[Submit][S ...

  4. BZOJ 4555: [Tjoi2016&Heoi2016]求和 [FFT 组合计数 容斥原理]

    4555: [Tjoi2016&Heoi2016]求和 题意:求\[ \sum_{i=0}^n \sum_{j=0}^i S(i,j)\cdot 2^j\cdot j! \\ S是第二类斯特林 ...

  5. [BZOJ 4555][Tjoi2016&Heoi2016]求和

    题意 给定 $n$ , 求下式的值: $$ f(n)= \sum_{i=0}^n\sum_{j=0}^i\begin{Bmatrix}i\\ j\end{Bmatrix}\times 2^j\time ...

  6. BZOJ 4555:[TJOI2016&HEOI2016]求和(第二类斯特林数+NTT)

    题目链接 \(Description\) 求 \[\sum_{i=0}^n\sum_{j=0}^iS(i,j)2^jj!\]对998244353取模后的结果. \(n<=10^5\) \(Sol ...

  7. bzoj 4555 [Tjoi2016&Heoi2016] 求和 —— 第二类斯特林数+NTT

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4555 关于第二类斯特林数:https://www.cnblogs.com/Wuweizhen ...

  8. bzoj 4555 [Tjoi2016&Heoi2016]求和——NTT+第二类斯特林数

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4555 第二类斯特林数展开式: \( S(i,j) = \frac{1}{j!} \sum\l ...

  9. 【bzoj4555】[Tjoi2016&Heoi2016]求和(NTT+第二类斯特林数)

    传送门 题意: 求 \[ f(n)=\sum_{i=0}^n\sum_{j=0}^i\begin{Bmatrix} i \\ j \end{Bmatrix}2^jj! \] 思路: 直接将第二类斯特林 ...

随机推荐

  1. Selenium自动化测试第一天(上)

    如有任何学习问题,可以添加作者微信:lockingfree 目录 Selenium自动化测试基础 Selenium自动化测试第一天(上) Selenium自动化测试第一天(下) Selenium自动化 ...

  2. NGUI组件整理总结

    一图流: 注意: private void RClickUI(Vector3 newPos) { this.gameObject.SetActive(true); this.transform.loc ...

  3. C++字符串拼接和输入

    一 .char类型字符串以空字符结尾 1.以空字符结尾,空字符被写作\0,其ASCII码为0,用来标记字符串的结尾. char dog[4]={'a','b','c','d'}   //不是一个字符串 ...

  4. docker创建redis镜像

    pull redis 镜像 创建redis的镜像有几种方式,可以直接从仓库中拉取,也可以采用dockerfile文件自己编译创建. 基于已有的redis镜像,docker可以采用run,或者creat ...

  5. vue.js学习之 如何在better-scroll加载完成后,自动滚动到最底部

    首先我们需要使用scrollTo这个方法: scrollTo(x, y, time, easing) 参数: {Number} x 横轴坐标(单位 px) {Number} y 纵轴坐标(单位 px) ...

  6. Catch That Cow(BFS广搜)

    Description Farmer John has been informed of the location of a fugitive cow and wants to catch her i ...

  7. python 项目配置虚拟环境

    # Windows 环境1, 安装 Visual C++ 2015 Build Tools, 依赖.Net Framework 4.6, 安装包位置 ./tools/windows/visualcpp ...

  8. P4语法(2) Parser

    这里参考学习了: P4语言规范 P4台湾社群 Parser 关于parser 在P4程序中,有着大量的首部(header)和首部实例,但每次只有部分首部实例会对数据包进行操作,而parser会用于生成 ...

  9. Debian常用软件

    1. 有道词典 https://github.com/justzx2011/openyoudao

  10. 【week2】 词频统计第一次更新

    词频统计: 对每个功能预计时间: 功能 预计(min) 实际(min) 数据流读入 20 40 正则规范字符串 15 20 排序 30 45 输出 20 30 其他   25 词频统计psp 日期 类 ...