1. 程式人生 > >動態虛樹計數

動態虛樹計數

需要 優秀 菊花 階乘 有關 取值 方法 循環 屬於

我們首先考慮沒有操作1和操作2怎麽做

分析一下lca(x,y)!=root這個條件。
也就是說,每一組中的任意兩個點,都需要屬於根節點的兩個不同兒子的子樹。
我們不妨求出根節點的每一個兒子中有多少個給出的點,這個直接用樹狀數組就能求出來。
這樣就得到了一個序列a1,a2...acnt。
這裏註意:這個地方cnt的大小是和根節點的度數無關的,cnt不會大於詢問中的k,因此不會被菊花圖卡。

得到這個序列後,轉化為這樣一個問題。
n種顏色,每種顏色有ai個,劃分為最多m組的方案數,每一組顏色不同。

首先枚舉一下組數o。
我們不妨考慮一波容斥,枚舉至少有幾組爆零了。
然後只需要對每一種顏色做一個組合數分配即可。
也就是∑k (-1)^k πi C(o-k,ai)。
這樣就可以m^2n的復雜度回答一組詢問,顯然還不夠優秀。

我們大力拆一波式子,把組合數拆為階乘的形式。
這樣我們對於那個內層的循環,就只需要維護三部分
第一部分:(o-k)!,連乘後就是個冪的形式。
第二部分:inv(ai!),連乘後是一個與k無關的變量,可以提前預處理。
第三部分:inv((o-k-ai)!) 連乘後是一個與o-k有關的變量。
由於o-k的取值只有m種,不妨提前預處理一發,對於每一個o-k處理出(o-k-ai)!的連乘。
然後就可以m^2回答一組詢問啦!

看起來m^2n是過不去的,但實際上,由於存在一個不等式,∑ m<=100000
(100000/m)∑m^2=100000*m。這樣復雜度就是對的啦!

然而,容斥的做法好像是很sb的,dp的方法好像很簡單,在此不做贅述。

動態虛樹計數