[Luogu5162]WD与积木(多项式求逆)
不要以为用上Stirling数就一定离正解更近,FFT都是从DP式本身出发的。
设f[i]为i个积木的所有方案的层数总和,g[i]为i个积木的方案数,则答案为$\frac{f[i]}{g[i]}$
转移枚举第一层是哪些积木:$$f_n=g_n+\sum_{i=1}^{n}\binom{n}{i}f_{n-i},f_0=0$$$$g_n=\sum_{i=1}^{n}\binom{n}{i}g_{n-i},g_0=1$$
转化成卷积形式:$$\frac{f_n}{n!}=\frac{g_n}{n!}+\sum_{i=1}^{n}\frac{1}{i!}\times \frac{f_{n-i}}{i!}$$$$\frac{g_n}{n!}=\sum_{i=1}^{n}\frac{1}{i!}\times \frac{g_{n-i}}{(n-i)!}$$
构造生成函数:$F(x)=\sum\frac{f_i}{i!}x^i$,$G(x)=\sum\frac{g_i}{i!}x^i$,$H(x)=\sum\frac{x^i}{i!}$。
则根据上式有:$F(x)=G(x)+F(x)(H(x)-1)-1$,$G(x)=G(x)(H(x)-1)+1$。
移项得:$F(x)=\frac{G(x)-1}{2-H(x)}=G(x)(G(x)-1)$,$G(x)=\frac{1}{2-H(x)}$。
多项式求逆即可。
#include<cstdio>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
using namespace std; const int N=,mod=;
int n,m,T,fac[N],h[N],g[N],f[N],inv[N],rev[N],tmp[N]; int ksm(int a,int b){
int res=;
for (; b; a=1ll*a*a%mod,b>>=)
if (b & ) res=1ll*res*a%mod;
return res;
} void DFT(int a[],int n,bool f){
for (int i=; i<n; i++) if (i<rev[i]) swap(a[i],a[rev[i]]);
for (int i=; i<n; i<<=){
int wn=ksm(,f ? (mod-)/(i<<) : (mod-)-(mod-)/(i<<));
for (int p=i<<,j=; j<n; j+=p){
int w=;
for (int k=; k<i; k++,w=1ll*w*wn%mod){
int x=a[j+k],y=1ll*w*a[i+j+k]%mod;
a[j+k]=(x+y)%mod; a[i+j+k]=(x-y+mod)%mod;
}
}
}
if (f) return;
int inv=ksm(n,mod-);
for (int i=; i<n; i++) a[i]=1ll*a[i]*inv%mod;
} void Inv(int a[],int b[],int l){
if (l==){ b[]=ksm(a[],mod-); return; }
Inv(a,b,l>>); int n=,L=;
for (; n<=l; n<<=) L++;
for (int i=; i<n; i++) rev[i]=(rev[i>>]>>)|((i&)<<(L-));
for (int i=; i<l; i++) tmp[i]=a[i],tmp[i+l]=;
DFT(tmp,n,); DFT(b,n,);
for (int i=; i<n; i++) tmp[i]=1ll*b[i]*(-1ll*tmp[i]*b[i]%mod+mod)%mod;
DFT(tmp,n,);
for (int i=; i<l; i++) b[i]=tmp[i],b[i+l]=;
} int main(){
n=;
fac[]=; rep(i,,n) fac[i]=1ll*fac[i-]*i%mod;
inv[n]=ksm(fac[n],mod-);
for (int i=n-; ~i; i--) inv[i]=1ll*inv[i+]*(i+)%mod;
rep(i,,n) h[i]=mod-inv[i]; h[]=;
for (m=; m<=n; m<<=); Inv(h,g,m);
for (int i=; i<m; i++) f[i]=g[i];
f[]=(g[]-+mod)%mod; m<<=;
DFT(f,m,); DFT(g,m,);
for (int i=; i<m; i++) f[i]=1ll*f[i]*g[i]%mod;
DFT(f,m,); DFT(g,m,);
for (scanf("%d",&T); T--; ) scanf("%d",&n),printf("%lld\n",1ll*f[n]*ksm(g[n],mod-)%mod);
return ;
}
[Luogu5162]WD与积木(多项式求逆)的更多相关文章
- Luogu5162 WD与积木(生成函数+多项式求逆)
显然的做法是求出斯特林数,但没有什么优化空间. 考虑一种暴力dp,即设f[i]为i块积木的所有方案层数之和,g[i]为i块积木的方案数.转移时枚举第一层是哪些积木,于是有f[i]=g[i]+ΣC(i, ...
- 洛谷 P5162 WD与积木【多项式求逆】
设f[i]为i个积木能堆出来的种类,g[i]为i个积木能堆出来的种类和 \[ f[n]=\sum_{i=1}^{n}C_{n}^{i}g[n-i] \] \[ g[n]=\sum_{i=1}^{n}C ...
- [luogu5162]WD与积木
设$g_{n}$表示$n$个积木放的方案数,枚举最后一层所放的积木,则有$g_{n}=\sum_{i=1}^{n}c(n,i)g_{n-i}$(因为积木有编号的所以要选出$i$个) 将组合数展开并化简 ...
- hdu 5730 Shell Necklace [分治fft | 多项式求逆]
hdu 5730 Shell Necklace 题意:求递推式\(f_n = \sum_{i=1}^n a_i f_{n-i}\),模313 多么优秀的模板题 可以用分治fft,也可以多项式求逆 分治 ...
- 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是第二类斯特林 ...
- NTT+多项式求逆+多项式开方(BZOJ3625)
定义多项式$h(x)$的每一项系数$h_i$,为i在c[1]~c[n]中的出现次数. 定义多项式$f(x)$的每一项系数$f_i$,为权值为i的方案数. 通过简单的分析我们可以发现:$f(x)=\fr ...
- Re.多项式求逆
前言 emmm暂无 多项式求逆目的 顾名思义 就是求出一个多项式的摸xn时的逆 给定一个多项式F(x),请求出一个多项式G(x),满足F(x)∗G(x)≡1(modxn),系数对998244353取模 ...
- BZOJ 3456: 城市规划 与 多项式求逆算法介绍(多项式求逆, dp)
题面 求有 \(n\) 个点的无向有标号连通图个数 . \((1 \le n \le 1.3 * 10^5)\) 题解 首先考虑 dp ... 直接算可行的方案数 , 容易算重复 . 我们用总方案数减 ...
- 洛谷P4841 城市规划(生成函数 多项式求逆)
题意 链接 Sol Orz yyb 一开始想的是直接设\(f_i\)表示\(i\)个点的无向联通图个数,枚举最后一个联通块转移,发现有一种情况转移不到... 正解是先设\(g(n)\)表示\(n\)个 ...
随机推荐
- php魔术函数 __clone()
原文地址: http://www.nowamagic.net/librarys/posts/php/32 PHP4面向对象功能一个很大的缺点,是将对象视为另一种数据类型,这使得很多常见的OOP方法无法 ...
- Ubuntu 14.04 + xRDP + Xfce 实现Windows远程桌面连接
1. 安装xRDP及vncserver sudo apt-get install xrdp sudo apt-get install vnc4server tightvncserver 2. 安装Xf ...
- VUE项目用hbuilder 打包为手机APP
一.测试项目是否可以正确运行 指令:npm run dev 首先我们先建立一个vue的项目,本人用的是vue-cli随便建立的,然后运行项目 不必非得是像我这样的,这一步的目的只是测试一下咱们的 ...
- VC++6.0中ClassView中类消失 解决方案[转自网络]
有时候在VC++6.0中编程会出现这样一个问题,由于对C...View类的操作后,在窗口左边ClassView框中的C...View类会消失,这种操作通常是在C...View类中右击点“Add Win ...
- Linux下配置镜像源
清华大学地址: https://mirrors.tuna.tsinghua.edu.cn 选择对应ubuntu的版本 在linux下用终端敲 cd /etc/apt/source.list 把里面的内 ...
- ExtJs对js基本语法扩展支持
ExtJs对js基本语法扩展支持 本篇主要介绍一下ExtJs对JS基本语法的扩展支持,包括动态加载.类的封装等. 一.动态引用加载 ExtJs有庞大的类型库,很多类可能在当前的页面根本不会用到,我们可 ...
- 面试经典问题---数据库索引B+、B-树
具体讲解之前,有一点,再次强调下:B-树,即为B树.因为B树的原英文名称为B-tree,而国内很多人喜欢把B-tree译作B-树,其实,这是个非常不好的直译,很容易让人产生误解.如人们可能会以为B-树 ...
- sqlserver导出为EXcel--CSV格式
DataTable dt = Connect.BindTable(" SELECT 名称,地址,当前日期 FROM table GROUP BY 名称,地址,当前日期 order ...
- GreenPlum学习笔记:date_part与extract提取日期时间、时间差
GP可以使用date_part / extract从日期时间类型中抽取部分内容. 方法一:extract 格式:extract(field from source) extract函数从日期.时间数 ...
- 1089: [SCOI2003]严格n元树
好久没更新了..于是节操掉尽python水过本来就水的题.. n,d=map(int, raw_input().split()) if d==0: print 1 else: f=[1] for i ...