prufer序列總結
阿新 • • 發佈:2021-10-04
prufer 序列
基礎知識
\(prufer\) 序列是一種 \(n\) 個節點的有標號無根樹與 \(n-2\) 的序列的雙射關係
樹轉序列:每次選出編號最小的 葉節點,將其刪去,並將其父親加入序列,直到還剩兩個點
線性構建:
void T_P(){ for(int i=1;i<n;i++)fa[i]=read(),deg[fa[i]]++; for(int i=1,j=1;i<=n-2;i++,j++){ while(deg[j])j++; p[i]=fa[j]; while(i<=n-2&&(!(--deg[p[i]]))&&p[i]<j)p[i+1]=fa[p[i]],i++; } }
序列轉樹:列舉最小的點,連向序列的第一個元素
void P_T(){
for(int i=1;i<=n-2;i++)p[i]=read(),deg[p[i]]++;p[n-1]=n;
for(int i=1,j=1;i<=n-1;i++,j++){
while(deg[j])j++;
fa[j]=p[i];
while(i<n-1&&(!(--deg[p[i]]))&&p[i]<j)fa[p[i]]=p[i+1],i++;
}
}
prufer序列的性質
- 由於對映關係唯一,那麼樹的個數由序列的個數決定,於是 \(n\)
- 最後剩下的兩個點,一定有一個是編號最大的點
- 考慮最後剩下的一條邊一定是編號最大點向其父親(或其最大編號的兒子)的連邊,那麼序列裡的剩下 \(n-2\) 個數恰好對應樹裡剩下的邊
- 一個度數為 \(deg\) 的節點其在 \(prufer\) 序列裡出現 \(deg-1\) 次
經典例題
考慮由性質可知,對於點 \(i\),在序列中出現 \(deg_i-1\) 次
序列總長度為 \(n-2\),每個點出現 \(deg_i-1\) 次,相當於多重集的排列,答案即為:\(\frac{n-2}{\prod deg_i-1}\)
設每個連通塊點的個數為 \(s_i\),那麼如果這個連通塊向外總度數為 \(d_i\),那麼方案數為 \(s_i^{d_i}\)
那麼對於每個 \(d_i\) 序列,答案為 \(\displaystyle\binom{k-2}{d_1,d_2,...,d_k}\prod s_i^{d_i}\)
發現和多項式定理類似
於是轉化為 \((d_1+d_2+...+d_k)^{k-2}\prod s_i\)
即 \(n^{k-2}\prod s_i\)
可以看做揹包模型,將每個點看做價值為 \(f(deg_i)\),體積為 \(deg_i-1\) 的物品去填充體積為 \(n-2\) 的揹包
揹包過程中可以順便記錄轉移,之後用 \(prufer\) 將序列轉化成樹