[ZJOI2015] 地震后的幻想乡(状压dp + 期望)
problem
luogu-P3343
solution
dp(i):dp(i):dp(i): 當(dāng)恰好加入第 iii 小邊時(shí)候,所有點(diǎn)聯(lián)通的方案數(shù)。
則 ans=∑idpi(mi)im+1ans=\sum_i \frac{dp_i}{\binom mi}\frac{i}{m+1}ans=∑i?(im?)dpi??m+1i? 。
重點(diǎn)是如何計(jì)算出 dp(i)dp(i)dp(i)。
這個(gè)恰好的限制不好搞。加第 iii 小的邊之前不能提前聯(lián)通,加后一定要聯(lián)通。
轉(zhuǎn)化一下,dp(i)=dp(i)=dp(i)= 加之前不連通的方案數(shù) ?-? 加之后不連通的方案數(shù)。
記 f(s,i):sf(s,i):sf(s,i):s 點(diǎn)集中的點(diǎn)之間連了 iii 條邊后 sss 中的點(diǎn)仍然不連通的方案數(shù)。
記 g(s,i):sg(s,i):sg(s,i):s 點(diǎn)集中的點(diǎn)之間連了 iii 條邊后 sss 中的點(diǎn)聯(lián)通的方案數(shù)。
顯然 f(s,i)+g(s,i)=(cnt(s)i)f(s,i)+g(s,i)=\binom{cnt(s)}{i}f(s,i)+g(s,i)=(icnt(s)?),其中 cnt(s):cnt(s):cnt(s): 點(diǎn)集 sss 中的點(diǎn)之間的邊數(shù)。
轉(zhuǎn)移枚舉 sss 的子集 ttt,滿足 s&(?s)s\&(-s)s&(?s),即 sss 中最小元素點(diǎn)也在 ttt 集合內(nèi)。
f(s,i)=∑(s&?s)∈t?s∑j=0ig(t,j)(s⊕ti?j)f(s,i)=\sum_{(s\&-s)\in t\subset s}\sum_{j=0}^ig(t,j)\binom{s\oplus t}{i-j} f(s,i)=(s&?s)∈t?s∑?j=0∑i?g(t,j)(i?js⊕t?)
這種轉(zhuǎn)移相當(dāng)于以 sss 中最小元素點(diǎn)為參考,其所在的聯(lián)通塊為 ttt,其余看作不連通,且 (s⊕ti?j)\binom{s\oplus t}{i-j}(i?js⊕t?) 任意選的邊連出來(lái)的集合一定不與 ttt 有邊相連。這樣就不會(huì)算重了。
最后 dpi=f({1,2,...,n},i?1)?f({1,2,...,n},i)dp_i=f(\{1,2,...,n\},i-1)-f(\{1,2,...,n\},i)dpi?=f({1,2,...,n},i?1)?f({1,2,...,n},i)。
在代碼實(shí)現(xiàn)中統(tǒng)計(jì)答案略有不同,我是將這個(gè)式子稍微展開(kāi)了一下。
ans=∑i=1mim+1f({1,2,...,n},i?1)?f({1,2,...,n},i)(mi)ans=\sum_{i=1}^m\frac{i}{m+1}\frac{f(\{1,2,...,n\},i-1)-f(\{1,2,...,n\},i)}{\binom mi} ans=i=1∑m?m+1i?(im?)f({1,2,...,n},i?1)?f({1,2,...,n},i)?
考慮相鄰兩位:
im+1f({1,2,...,n},i?1)?f({1,2,...,n},i)(mi)i+1m+1f({1,2,...,n},i)?f({1,2,...,n},i+1)(mi+1)\frac{i}{m+1}\frac{f(\{1,2,...,n\},i-1)-f(\{1,2,...,n\},i)}{\binom mi}\\ \frac{i+1}{m+1}\frac{f(\{1,2,...,n\},i)-f(\{1,2,...,n\},i+1)}{\binom m{i+1}} m+1i?(im?)f({1,2,...,n},i?1)?f({1,2,...,n},i)?m+1i+1?(i+1m?)f({1,2,...,n},i)?f({1,2,...,n},i+1)?
將 1m+1\frac{1}{m+1}m+11? 提出來(lái),發(fā)現(xiàn) i??f({1,2,...,n},i)i*-f(\{1,2,...,n\},i)i??f({1,2,...,n},i) 且 (i+1)?+f({1,2,...,n},i)(i+1)*+f(\{1,2,...,n\},i)(i+1)?+f({1,2,...,n},i),相加其實(shí)就是加入了一次 f({1,2,...,n},i)f(\{1,2,...,n\},i)f({1,2,...,n},i)。
而 f({1,2,...,n},m)=0f(\{1,2,...,n\},m)=0f({1,2,...,n},m)=0,不可能所有邊都加完了還不聯(lián)通。
所以,有:
ans=1m+1∑i=0mf({1,2,...,n},i)(mi)ans=\frac{1}{m+1}\sum_{i=0}^m\frac{f(\{1,2,...,n\},i)}{\binom mi} ans=m+11?i=0∑m?(im?)f({1,2,...,n},i)?
code
#include <bits/stdc++.h> using namespace std; #define double long double #define int long long int n, m; int cnt[1 << 10]; double c[50][50]; int f[1 << 10][50], g[1 << 10][50]; struct node { int u, v; }E[50];signed main() {scanf( "%lld %lld", &n, &m );for( int i = 1;i <= m;i ++ ) scanf( "%lld %lld", &E[i].u, &E[i].v );for( int s = 0;s < (1 << n);s ++ )for( int i = 1;i <= m;i ++ )if( (s >> E[i].u - 1 & 1) and (s >> E[i].v - 1 & 1) )cnt[s] ++;for( int i = 0;i <= m;i ++ ) {c[i][0] = c[i][i] = 1;for( int j = 1;j < i;j ++ ) c[i][j] = c[i - 1][j - 1] + c[i - 1][j];}for( int s = 0;s < (1 << n);s ++ )for( int i = 0;i <= cnt[s];i ++ ) {for( int t = s;t;t = (t - 1) & s )if( t & (s & -s) )for( int j = 0;j <= min( cnt[t], i );j ++ )f[s][i] += g[t][j] * c[cnt[s ^ t]][i - j];g[s][i] = c[cnt[s]][i] - f[s][i];}double ans = 0;for( int i = 0;i <= m;i ++ ) ans += 1.0 / (m + 1) * f[(1 << n) - 1][i] / c[m][i];printf( "%Lf\n", ans );return 0; }總結(jié)
以上是生活随笔為你收集整理的[ZJOI2015] 地震后的幻想乡(状压dp + 期望)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 春天的气息的优美句子
- 下一篇: 灰色卫衣衣服颜色搭配技巧 灰色卫衣衣服怎