关于卡特兰数这玩意,其实最早是为了准备NOIP初赛而学的(包括斯特林数),不过那时候也没意识到它这么好玩。
这几天好像经常看到关于卡特兰数的一些应用,尤其是文化课数学正好在学计数,所以就决定写一篇总结一下。
为了给非竞赛生更好的阅读体验不至于一上来就被大量的公式劝退,我先介绍卡特兰数的应用,再推导公式。
当你看到这些时,它对应了卡特兰数
我们用
Cn表示第
n个卡特兰数,其中
n∈N。它满足以下递推公式:
Cn=i=0∑n−1CiCn−1−i=i+j=n−1∑CiCj(n∈N∗)
C0=1
另外还有一个更简洁的递推公式
Cn=n+14n−2Cn−1,但它的使用频率并不高。
以及通项
Cn=n+11C2nn。这个公式的推导我放在最后。
如果你发现你要解决的计数问题对应到以上公式,考虑卡特兰数。
应用举栗
- 【可接受数列问题】由
n个
−1和
n个
+1构成的长度为
2n的数列
a1,a2,⋯,a2n,如果满足对于任意的
k≤2n且
k∈N∗都有
a1+a2+⋯+ak≥0
那么称这个数列是可接受的,否则是不可接受的。可以证明:可接受的数列个数是第
n个卡特兰数
Cn。
证: 首先,由
n个
−1和
n个
+1构成的长度为
2n的数列显然有
C2nn种,它们要么是可接受的,要么是不可接受的。我们想办法求出其中的不可接受的数列数量,将其减去即可。
考虑一个不可接受的数列,那么它一定存在第一个下标
k,满足
a1+a2+⋯+ak<0
显然
k是一个奇数,
ak=−1,并且前
k−1个数中
−1的个数和
+1一样多。
下面我们做一个操作:将
a1,⋯,ak这
k个数全部取相反数,即
+1变为
−1,
−1变为
+1,那么
−1的个数减少
1,
+1的个数增加
1,我们得到了一个由
(n−1)个
−1和
(n+1)个
+1构成的长度为
2n的数列。
上述操作是可逆的。即,对于任意一个由
(n−1)个
−1和
(n+1)个
+1构成的数列,我们都可以找到其最小的下标
k满足前
k项之和大于
0(这样的
k显然存在),将这
k项取相反数,得到一个不可接受的数列。
所以,不可接受的数列与由
(n−1)个
−1和
(n+1)个
+1构成的长度为
2n的数列一样多,有
C2nn+1种。
因此,可接受的数列数量为
C2nn−C2nn+1,化简得它等于
n+11C2nn,为第
n个卡特兰数。
- 【下对角线格点路径问题】在直角坐标系中,从
(0,0)走到
(n,n),只能向右或向上走的所有格点路径中,只经过直线
y=x及其下方区域的点(不能穿过直线
y=x)的路径数为第
n个卡特兰数
Cn
证: 利用上一题的结论,不妨将向右走记为
+1,向上走记为
−1,那么每条路径都与一个由
n个
+1和
n个
−1构成的序列一一对应,而满足要求(即所谓“下对角线格点路径”)的格点路径对应的序列就是可接受序列,数量为
Cn。
当
n不大时,本题还有一个简单易行的动态规划做法:设
f(i,j)表示从
(0,0)走到
(i,j)的下对角线格点路径数,当
i<j时
f(i,j)=0,否则
f(i,j)=f(i,j−1)+f(i−1,j)。这个做法尤其对非竞赛生比较友好,因为它其实就是小学老师教过的在格点上标数字的做法:
![下对角线格点路径](https://img-blog.csdnimg.cn/20190420084438683.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzM5Njc3Nzgz,size_16,color_FFFFFF,t_70)
其实可接受数列问题也可以转化成这道题然后采用这个做法,枚举量和思维量都比较小。当然了,真正算法竞赛里是肯定不会让这种做法拿到满分的。
- 【多边形的三角剖分问题】将一个凸
(n+2)边形通过连接
(n−1)条不相交的对角线的方式剖分成
n个三角形的方案数为第
n个卡特兰数
Cn。
证: 设
fn表示凸
(n+2)边形三角剖分方案数,我们可以选定一个顶点
A1,从它出发连接两条线段
A1Ai和
A1Ai+1(允许其中的某一条是该多边形的边而非对角线),那么这两条线段和
AiAi+1构成了一个三角形。这也就把这个凸
(n+2)边形切成了一个凸
i边形
A1A2⋯Ai、一个三角形
A1AiAi+1和一个凸
(n−i+3)边形
A1Ai+1Ai+2⋯An+2,根据乘法原理,继续剖分的方案数为
fi−2fn−i+1,于是有
fn=i=2∑n+1fi−2fn−i+1=i=0∑n−1fifn−1−i
并且规定“二边形”三角剖分方案数为
1,有
f0=1
可以发现
fn=Cn,为第
n项卡特兰数。
- 【圆上的点连线问题】将圆上的
2n个等分点成对地连线,使得这
n条线段互不相交的方案数为
Cn。
证: 设
fn表示将圆上的
2n个等分点成对连线,使得它们不相交的方案数。我们可以选定一个点
A1,任意连接一条线段
A1Ai。这里
i显然是偶数(否则它两侧的点的个数均为奇数,没有符合条件的方案),不妨用
2i来表示,即连接线段
A1A2i,那么在它两侧的点数分别为
(2i−2)和
(2n−2i)个,根据乘法原理,继续连线的方案数为
fi−1fn−i。所以有
fn=i=1∑nfi−1fn−i=i=0∑n−1fifn−1−i
并且规定
n=0时有一种方案
f0=1
不难发现
fn=Cn。
- 【二叉树计数问题】由
n个结点构成的不同形态的有根二叉树共有
Cn个,其中
Cn为第
n项卡特兰数。
仿照上例显然。
- 【进出栈序列问题】将
n个不同的元素依次进栈,可以得到不同的出栈序列有
Cn个。
令进栈为
+1,出栈为
−1,则变成了可接受数列问题。
- 【表达式运算顺序问题】考虑将
(n+1)个数相乘
a1a2⋯an+1
现在允许给这个表达式加括号来改变运算顺序,但是不可以改变它们的位置,即可以使用结合律但不能使用交换律,不同的运算顺序有
Cn种。
同样从递推关系入手考虑即可得证。
公式推导
下面我们来推导卡特兰数通项公式
前置芝士:生成函数
设有数列
{fn},其生成函数定义为
F(x)=f0+f1x+f2x2+⋯,即
F(x)=k=0∑∞fkxk,由于这里
x并无实际意义,规定
∣x∣<∣fi∣1。
前置芝士:牛顿二项式定理
即二项式定理的扩展:
(a+b)α=k=0∑∞Cαkaα−kbk,其中
α是任意实数。
Cαk为牛顿二项式系数,定义为
Cαk=k!α(α−1)(α−2)⋯(α−k+1)=k!αk,其中
αk称为
α的
k次下降阶乘幂。(这个记号来源于《具体数学》)
设卡特兰数列生成函数
f(x)=C0+C1x+C2x2+⋯=k=0∑∞Ckxk
(f(x))2=C0C0+(C0C1+C1C0)x+(C0C2+C1C1+C2C0)x2+⋯
即
(f(x))2=k=0∑∞⎝⎛i+j=k∑CiCj⎠⎞xk
将递推公式代入得到
(f(x))2=k=0∑∞Ck+1xk
x(f(x))2=k=0∑∞Ck+1xk+1=k=1∑∞Ckxk=f(x)−C0
于是得到关于
f(x)的二次方程
x(f(x))2−f(x)+1=0
利用求根公式解得
f(x)=2x1±1−4x
注意到
f(x)必须满足
f(0)=C0=1。当
f(x)=2x1−1−4x
时,利用洛必达法则可得
x→0limf(x)=1符合。然而当
f(x)=2x1+1−4x
时,不难发现它在
0处的极限不存在(为无穷大),舍去。
所以
f(x)=2x1−1−4x
利用牛顿二项式定理展开,最终可以得到
f(x)=k=0∑∞(k+1)!k!(2k)!xk
所以
Cn=(n+1)!n!(2n)!=n+11C2nn
如果希望得到本文一开始提到的那个更简洁的递推公式,只需将两项的通项相除即可。
练习:
- 更一般地,从
(0,0)走到
(n,m)(
n≥m)的下对角线格点路径数是多少?
- [TJOI2015]概率论:由
n个顶点随机生成的有根二叉树期望有多少个叶节点?
- 我也想不到有什么别的练习题了…
参考资料:《组合数学(原书第5版)》 by Richard A. Brualdi