tree
随机走,看期望
由于zzn过于sb,考试推出来式子因为统计时间不对没有$AC$(应dfs前统计)
zzn实在过于sb,式子和题解完全不一样,所以看题解的可以走了
记录tofa[x]表示当前点走到父亲期望步数
可以直接走到父亲 贡献$\frac{1}{deg[x]}$
走到儿子再走到父亲$\frac{1}{deg[x]}*(1+tofa[y]+tofa[x]) $解释一下,花一步走到$y$,花$tofa[y]$走到$x$最后还是要走到$fa$
总$tofa[x]=\frac{1}{deg[x]}+\sum\limits_{y}^{y\in son[x]} \frac{1}{deg[x]} (1+tofa[y]+tofa[x])$
记录toson[x]表示从父亲走到x步数
考虑toson[y]转移
从$x$直接走到$y$ $\frac{1}{deg[x]}$
走到$x$父亲再走到$y$ $\frac{1}{deg[x]}*(toson[x]+1+toson[y])$
走到$y$兄弟走到$y$ $\frac{1}{deg[x]}*(1+tofa[y]+toson[y])$
总$toson[y]=\frac{1}{deg[x]}+\frac{1}{deg[x]}*(toson[x]+1+toson[y]) +\sum\limits_{y2}^{y2\in son[x] \& y2!=y} *(1+tofa[y2]+toson[y])$
然后移项
$tofa[x]=deg[x]+\sum\limits_{y}^{y\in son[x]}tofa[y]$
$toson[y]=deg[x]+toson[x]+\sum\limits_{y2}^{y2\in son[x] \& y2!=y} tofa[y2]$
统计即可
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<bits/stdc++.h> using namespace std; #define ll long long #define A 222222 ll n,tot,canqj; ll vis[A],nxt[A],head[A],ver[A]; double f[A],dis[A],tofa[A],toson[A],deg[A]; void add(ll x,ll y){ nxt[++tot]=head[x],head[x]=tot,ver[tot]=y; } void dfs(ll x,ll pre){ for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; f[y]=2+f[x]; dis[y]=dis[x]+f[x]; dfs(y,x); } } void dpfs1(ll x,ll pre){ tofa[x]=deg[x]; for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; dpfs1(y,x); tofa[x]+=tofa[y]; } // printf("tofa[%lld]=%.3lf\n",x,tofa[x]); } void dpfs2(ll x,ll pre){ ll sum=0; for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; toson[y]=deg[x]+toson[x]; sum+=tofa[y]; // printf("toson[%lld]=%.3lf\n",y,toson[y]); } for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; toson[y]+=sum-tofa[y]; // printf("toson[%lld]=%.3lf\n",y,toson[y]); } for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; dpfs2(y,x); } } void dfs3(ll x,ll pre){ for(ll i=head[x];i;i=nxt[i]){ ll y=ver[i]; if(y==pre) continue ; dis[y]=dis[x]+toson[y]; dfs3(y,x); // printf("dis[%lld]=%.3lf dis[%lld]=%.3lf\n",y,dis[y],x,dis[x]); } } int main(){ scanf("%lld",&n); f[1]=1; dis[1]=1; canqj=1; for(ll i=1,a,b;i<n;i++){ scanf("%lld%lld",&a,&b); add(a,b);add(b,a); deg[a]++,deg[b]++; if(deg[a]>2||deg[b]>2) canqj=0; } /* dfs(1,0); for(ll i=1;i<=n;i++){ printf("%.3lf\n",dis[i]); } */ for(ll i=head[1];i;i=nxt[i]){ ll y=ver[i]; toson[y]=1; } for(ll i=2;i<=n;i++){ if(deg[i]==1){ tofa[i]=1; } } // memset(dis,0,sizeof(dis)); dis[1]=1; dpfs1(1,0); dpfs2(1,0); dfs3(1,0); for(ll i=1;i<=n;i++){ printf("%.3lf\n",dis[i]); } // } }