卡特兰数 Catalan number 是一个数列,可以用在计算 n 个元素进出栈的情况数目。例如一个序列以 1 2 3 4
的顺序入栈,有多少种出栈情况?
理论
推导过程如下,主要使用了分治思想。
一个序列的入栈顺序确定,那么出栈顺序就有了限制
- 某元素出栈必须在入栈之后
- 某元素出栈必须在栈顶
将出入栈顺序放在一起,可以划分为多种情况,每种情况都是分为两个部分,分界线为栈空。 下面以带圈为入栈,不带圈为出栈说明,入栈顺序确定 $\textcircled{1}\textcircled{2}\textcircled{3}\textcircled{4}$ , 出入栈顺序可以是 $\textcircled{1}1|\textcircled{2}2\textcircled{3}3\textcircled{4}4$ 、 $\textcircled{1}\textcircled{2}21|\textcircled{3}3\textcircled{4}4$ 、 $\textcircled{1}\textcircled{2}2\textcircled{3}31|\textcircled{4}4$ 等。
在竖线 |
处第一次出现栈空,将出入栈顺序划分为两部分,这两部分是两个更小的本类子问题。
由于要求栈空,第一个入栈元素必须最后一个出栈,实际第一个子问题是一个元素个数-1 的子问题。
根据乘法法则和加法法则,可以得到本类问题的递推公式:
设 $n$ 个元素以确定顺序入栈有 $f(n)$ 种出栈情况,则
规定 $f(0)=1$ 且 $n\ge1$,接下来是数学问题,推导过程日后研究。
摘抄网上的递推公式和通项公式:
$$f(n+1)=\dfrac{4n+2}{n+2}f(n)$$ $$f(n)=\dfrac{1}{n+1}C_{2n}^{n}=\dfrac{1}{n+1}\dfrac{(2n)!}{(n!)^2}$$编程
Julia 计算卡特兰数
|
|
Python
|
|
测试 Julia 和 Python 程序,毫无意外 Julia 性能更好。同时计算第 1_000_000 个卡特兰数,Julia 秒出,Python 宕机。
sympy 有一个 catalan 函数,比原生 Python 速度快,但相较于 Julia 还是乌龟慢。😀