Codeforces280 C. Game on Tree(期望dp)

题意:

在这里插入图片描述
点1为根。

解法:

染色操作可以等价于随机生成[1,n]的排列,
然后遍历排列,遇到没有染色的点就将其染色,并且操作次数+1,
总期望次数=每个点被染色的期望次数的和,

由于一轮下来每个点最多被染色一次,
所以每个点被染色的期望次数=全排列中这个点被染色的概率之和.
一个点会被染色只有当他的祖先都在这个点后面才行,
设sz[x]为x的祖先的数量(包含x),
x在长度为sz[x]的序列最前面的概率为1/sz[x],
因此被染色的期望次数为1/sz[x].1/sz[i]求和就是答案.

code:

#include <bits/stdc++.h>
using namespace std;
const int maxm=3e5+5;
vector<int>g[maxm];
int sz[maxm];//sz[x]表示x的祖先数量(包括自己)
int n;
void dfs(int x,int fa){
    
    
    sz[x]++;
    for(int v:g[x]){
    
    
        if(v==fa)continue;
        sz[v]+=sz[x];
        dfs(v,x);
    }
}
signed main(){
    
    
    cin>>n;
    for(int i=1;i<n;i++){
    
    
        int a,b;cin>>a>>b;
        g[a].push_back(b);
        g[b].push_back(a);
    }
    dfs(1,1);
    double ans=0;
    for(int i=1;i<=n;i++){
    
    
        ans+=1.0/sz[i];
    }
    printf("%.10f\n",ans);
    return 0;
}

猜你喜欢

转载自blog.csdn.net/weixin_44178736/article/details/112790827