ssy中學暑假集訓有關數學及多項式學習筆記

Lunar_Whisper發表於2024-08-18

8.16日 集訓倒數第\(7\)

唉,不知不覺間在ssy中學的暑假集訓就要結束了,只剩下一週的時間了,然而byn和yzh還有bao學姐\(21\)號就要走了,暑假就要過去了....

今天模擬賽的第二題很有意思,涉及到了許多的數學知識,正好來惡補一下:

淺談反演原理和二項式反演

首先來說說什麼是反演(inversion),對於一個序列\(\{f_i\}\)來說,如果存在另一個序列\(\{g_i\}\),使得以下公式成立:

\[g_n = \sum_{i=0}^{n}a_{ni}f_i \]

那麼反演其實就是利用\(g_0,g_1,g_2,...,gn\)來求出\(f\)序列,也就是把這個柿子變成:

\[f_n = \sum_{i=0}^{n}b_{ni}g_i \]

本質上來說,反演其實是一個解線性方程組的過程,但是你觀察後發現,這個矩陣實際上是一個三角矩陣,那必然存在著快捷的方法。對於使得這兩個反演公式成立的這些係數應該滿足什麼條件呢?我們現在就來探討一番!

反演原理

我們來考慮一下上面的那個柿子:
假設對於上面的任意\(0 \le n \le N\)都滿足以下柿子:

\[g_n = \sum_{i=0}^{n}a_{ni}f_i \]

那麼反演過後的柿子就是:

\[f_n = \sum_{i=0}^{n}b_{ni}g_i \]

那麼我們將\(g_i\)帶入就可以得到下面的式子:

\[\begin{aligned} f_n &= \sum_{i=0}^{n}b_{ni}\sum_{j=i}^{n}a_{nj}f_j(1) \\ &=\sum_{i=0}^{n}f_i \sum_{j=i}^{n}a_{nj}b_{nj} (2) \end{aligned} \]

這個時候問題出現了,為什麼\((1)\)的式子與\((2)\)相等呢?我們畫一個矩陣中的正三角來表示:

\[\begin{bmatrix} b_{n0}a_{00}f_0 & & & \\ b_{n1}a_{10}f_0 & b_{n1}a_{11}f_1 & & \\ b_{n2}a_{20}f_0 & b_{n2}a_{21}f_1 & b_{n2}a_{22}f_2 & \\ \vdots & \vdots & \ddots & \\ b_{nn}a_{n0}f_0 & b_{nn}a_{n1}f_1 & \cdots & b_{nn}a_{nn}f_n \\ \end{bmatrix} \]

顯然,\((1)\)的式子是按照矩陣中的式子一豎列一豎列來計算的,然後加起來;\((2)\)的式子是按照矩陣中的式子一行一行來計算的,然後加起來。由於整體不變,所以\((1) = (2)\)

反演的應用

接下來我們介紹二項式反演(binomial inversion),見下面的公式

\[f_n = \sum_{i=0}^{n}(-1)^iC_{n}^{i}g_i \Leftrightarrow g_n = \sum_{i=0}^{n}(-1)^iC_{n}^{i}f_i \]

這個是不是不太熟悉?我們介紹他的另一種情況:

\[f_n = \sum_{i=0}^{n}C_{n}^{i}g_i \Leftrightarrow g_n = \sum_{i=0}^{n}(-1)^{n-i}C_{n}^{i}f_i \]

證明不會寫,看這個或者代數證明是這個

那麼反演我們就先到這裡,接下來介紹二項式定理
這個很簡單,就是下面的這個式子:

\[(a+b)^n = \sum_{i=0}^{n}C_{n}^{i}a^{n-i}b^i \]

好了已經瞭解了這麼多的前置芝士接下來我們該做題目了!

二項式反演與二項式定理的綜合

給定\(N\)個點,求有標號DAG數量 \(mod 998244353\),不強制聯通。

\(f_i\)表示\(i\)個點的答案,首先我們欽定\(i\)個入度為\(0\)的點,然後連向其他的點,這樣會算重複,為什麼呢?看下面這個圖:

這個\(3\)點是\(1\)點和\(2\)點兩個入度為\(0\)的點所連線的點,可是\(3\)這個點卻被計算了兩次,這就是我們說的重複

接下來我們考慮如何避免重複,我們可以換種方法,我們欽定\(h_{i,j}\)表示\(i\)個點中至少選\(j\)個入度為\(0\)的點的總方案數,\(c_{i,j}\)表示\(i\)個點中恰好選\(j\)個入度為\(0\)的點的總方案數,那麼有以下公式:

\[h_{i,j} = \sum_{k=i}^{j}C_{k}^{j}c_{i,k} (1) \]

解釋一下奧:如果我們先不考慮一個圖中的不同情況數,那麼答案其實就是:

\[h_{i,j} = \sum_{k=i}^{j} c_{i,k} \]

為什麼要求和呢?還記得我們之前說\(h\)陣列和\(c\)陣列的定義嗎?\(h\)陣列是至少,所以對於恰好\(j\)個而言,他還需要補上\(j+1,j+2,...,m\),那麼因為求得是總和,所以我們要加上這一部分,那麼為什麼要加上
\(C_{k}^{j}\)呢?假設我們現在選取了了\(6\)個點,要從中選出\(3\)個,如下圖:

在下面這個圖中,選擇\(4\)個點的話可能性有\(C_{6}^{4}\)種,每次選出\(4\)個都要乘上對應的\(f_4\),這就構成了一種貢獻。

那麼對於式子\((1)\)而言,我們可以運用二項式反演匯出另一個式子:

\[c_{i,j} = \sum_{k = i}^{j}C_{k}^{j}(-1)^{k-j}h_{i,k} \]

那麼\(h_{i,j}\)很好求,首先要從\(i\)個點中選擇\(j\)個點,那麼運用組合數不難發現是\(C_{i}^{j}\),接下來我們就得到了兩個點集,一個擁有\(j\)個節點,另一個擁有\(i-j\)個節點,那麼由於這是一個DAG,所以對於\(j\)個節點連向\(i-j\)個節點,他的總方案數就是\(j(i-j)\),由於每條邊擁有兩種方向,所以也就是\(2^{j(i-j)}\)種可能性。我們計算的是擁有\(j\)個節點的那一個點集,同時我們也要考慮到那個\(i-j\)個點構成的另一個點集,所以答案又要乘上\(f_{i-j}\)。所以\(h_{i,j}\)就等於:

\[h_{i,j} = C_{i}^{j}2^{j(i-j)}f_{i-j} \]

相關文章