生成函数是一种用级数的系数来表达数列的方法,是处理数列的最强有力的方法之一。在 OI 中生成函数常常与多项式结合起来处理计数问题。

几种基本的生成函数

对于一个无限长度的数列 $a_0, a_1, a_2, \ldots$,它的普通型生成函数 (Ordinary Generating Function, OGF) 是

$$ F(z)=a_0+a_1z+a_2z+\ldots+a_iz^i+\ldots $$

它的指数型生成函数 (Exponential Generating Function, EGF) 是

$$ F(z)=\dfrac{a_0}{0!}+\dfrac{a_1z}{1!}+\dfrac{a_2z^2}{2!}+\ldots+\dfrac{a_iz^i}{i!}+\ldots $$

还有另一种较为特殊的狄利克雷型生成函数,暂时不提。

普通型生成函数

普通型生成函数是我们最常用的生成函数。在这之后,如果不说明是何种生成函数,默认是在指普通型生成函数。

数列 $1,1,1,\ldots$ 的普通型生成函数是什么?

这个问题似乎很无趣。让我们把它写下来

$$ F(z)=1+z+z^2+\ldots\ zF(z)=z+z^2+z^3+\ldots $$

我们发现

$$ F(z)-zF(z)=1\ F(z)=\dfrac{1}{1-z} $$

事实上,$1+z+z^2+\ldots$ 是 $F(z)$ 的开放形式,而 $\dfrac{1}{1-z}$ 是 $F(z)$ 的封闭形式。用相同的方法,我们能得到所有类似数列的普通型生成函数的封闭形式:

$$ F(z)=1+az+a^2z^2+a^3z^3\ldots=\dfrac{1}{1-az}\ G(z)=1+z^{a}+z^{2a}+z^{3a}+\ldots=\dfrac{1}{1-z^a} $$

如果你把 $z=10$ 代入 $1+z+z^2+\ldots=\dfrac{1}{1-z}$,你会发现这个式子根本不成立。事实上,这个式子只有在 $|z|<1$,即 $z^{+\infty}=0$ 时才成立。

幸运的是,在生成函数中我们只关心 $F(z)$ 的系数,不关心 $z$ 的值和 $F(z)$ 的值。可以认为这些封闭形式在我们研究的范围内总是成立的。

数列 $\binom{n}{0},\binom{n}{1},\binom{n}{2},\ldots,\binom{n}{i},\ldots$ 的普通型生成函数是什么?

这个问题和上面那个大同小异。直接写出来

$$ F(z)=\binom{n}{0}+\binom{n}{1}z+\binom{n}{2}z^2+\ldots $$

这符合二项式定理的形式。用二项式定理得到原式的封闭形式:

$$ F(z)=(1+z)^n $$

看来很多数列都有封闭形式!斐波那契数列是否也有封闭形式?

$$ F(z)=1+z+2z^2+3z^3+5z^4+8z^7+\ldots $$

因为 $f_n=f_{n-1}+f_{n-2}$,于是对于原函数的每一项 $f_iz^i$,我们都可以用 $f_iz^i=z\cdot f_{i-1}z^{i-1}+z^2\cdot f_{i-2}z^{i-2}$ 替换

$$ F(z)=1+zF(z)+z^2F(z) $$

解得

$$ F(z)=\dfrac{1}{1-z-z^2} $$

普通型生成函数卷积

生成函数如果不能进行运算,那它将是无用的。我们先介绍生成函数的卷积运算。你也可以认为卷积就是乘法。

普通型生成函数的卷积与多项式类似。设普通型生成函数 $F(z)=\sum\limits_{i=0} f_iz^i$ 和 $G(z)=\sum\limits_{i=0} g_iz^i$,则有 $(F*G)(z)=\sum\limits_{i=0}\sum\limits_{j=0}^if_jg_{i-j}z^i$。这样定义是很自然的,因为乘法分配律。

我们发现这像是一个动态规划的转移。如果把 $F$,$G$ 和 $FG$ 看做三个数组,则对于 $FG$ 的每个元素,都有

$$ (F*G)[i]=F[0]\times G[i]+F[1]\times G[i-1]+F[2]\times G[i-2]+F[3]\times G[i-3]+\ldots+F[i]\times G[0] $$

这个 DP 的转移原本是 $O(n^2)$ 的。但如果我们把它看成生成函数的卷积,就可以在 $O(n\log n)$ 的时间复杂度内计算。

当然,生成函数不止能优化时间,它还是一种更简便的计算工具。参考下面的例题:

你们家将要外出野餐,由你负责准备食物。你打算携带一些水、牛奶、饼干、三明治和火腿。考虑到食物搭配合理,你准备的食物要满足如下条件:

  • 水携带任意瓶
  • 牛奶携带 $0$ 瓶或 $2$ 瓶
  • 饼干携带 $3$ 盒或 $4$ 盒
  • 三明治携带偶数份
  • 火腿携带奇数份

若一共携带 $1000$ 件食物,有多少种携带方案?两个方案不同当且仅当在这两种方案中,某种食物的数量不同。

携带水的方案数形成的数列是 $1, 1, 1, \ldots$ (携带任意瓶水的方案数都是 $1$)。由前面介绍的知识可知携带水的方案数的生成函数是 $\dfrac{1}{1-x}$。

携带牛奶的方案数形成的数列是 $1, 0, 1, 0, 0, 0 \ldots$ (只有携带 $0$ 瓶或 $2$ 瓶的方案数是 $1$)。它的生成函数是 $1+x^2$。

携带饼干的方案数形成的数列是 $0, 0, 0, 1, 1, 0, 0, \ldots$。它的生成函数是 $x^3+x^4$。

携带三明治的方案数形成的数列是 $1, 0, 1, 0, 1, 0, \ldots$。它的生成函数是 $1+x^2+x^4+x^6+\ldots=\dfrac{1}{1-x^2}$。

携带火腿的方案数形成的数列是 $0, 1, 0, 1, 0, 1, \ldots$。它的生成函数是 $\dfrac{x}{1-x^2}$。

由于转移的形式与生成函数的卷积的形式完全吻合,这些生成函数的卷积的 $x^{1000}$ 次项的系数就是答案。于是携带食物的方案数形成的数列的生成函数是

$$ \dfrac{1}{1-x}(1+x^2)(x^3+x^4)\dfrac{1}{1-x^2}\dfrac{x}{1-x^2}=\dfrac{x^4+x^5+x^6+x^7}{(1-x)(1-x^2)^2} $$

由于包含除法,我们现在还不会求 $\dfrac{x^4+x^5+x^6+x^7}{(1-x)(1-x^2)^2}$ 的系数。但我们已经得到了复杂情况的简洁表达方式。

指数型生成函数

为什么指数型生成函数被称为指数型生成函数,而不是阶乘型生成函数?因为指数函数的麦克劳林级数是

$$ e^x = \sum\limits_{i=0}^{+\infty}\dfrac{x^i}{i!} $$

我们也常把 $e^x$ 写作 $\exp x$。可以看出 $\exp x$ 正好与指数型生成函数的形式吻合。

由于 $\binom{n}{m}=\dfrac{n!}{m!(n-m)!}$,指数型生成函数的卷积恰好满足 $(F*G)(z)=\sum\limits_{i=0}\sum\limits_{j=0}^i\binom{i}{j}f_jg_{i-j}z^i$,正好比 OGF 多了一个二项式系数。下面的例题可以帮助理解这里的二项式系数的作用。

科学家最近在火星上发现了一种原始生物。这种原始生物也是以 DNA 作为遗传物质的。

我们可以用一个仅含 $\texttt{A,T,G,C}$ 的字符串来描述这个生物的某个基因片段。经过研究,科学家发现这个字符串满足如下限制:

  • $\texttt{A}$ 的出现次数为偶数
  • $\texttt{T}$ 的出现次数为奇数

求有多少个满足如上限制且长度为 $n$ 的字符串。

由于字符间的不同顺序也要计入方案,在转移时我们要乘上对应的二项式系数。指数型生成函数正好可以担负这一任务。

$\texttt{A}$ 的方案数的指数型生成函数是 $1+\dfrac{x^2}{2!}+\dfrac{x^2}{2!}+\dfrac{x^4}{4!}+\ldots=\dfrac{e^x + e^{-x}}{2}$。

$\texttt{T}$ 的方案数的指数型生成函数是 $\dfrac{x}{1!}+\dfrac{x^3}{3!}+\dfrac{x^5}{5!}+\ldots=\dfrac{e^x-e^{-x}}{2}$。

$\texttt{G}$ 和 $\texttt{C}$ 的方案数的指数型生成函数都是 $e^x$。

于是字符串的方案数的指数型生成函数就是

$$\dfrac{e^x + e^{-x}}{2}\dfrac{e^x - e^{-x}}{2}e^xe^x=\dfrac{e^{4x}-1}{4}$$

用麦克劳林级数展开就可以得到各项系数了。这个生成函数的第 $n$ 项系数就是答案。

更高阶的生成函数运算

事实上这一类类多项式生成函数还可以求指数函数、对数函数、平方根甚至三角函数。其中,指数函数有组合意义,对数函数则是这一组合意义的反演。

例题

付公主的背包
The Child and Binary Tree