Codeforces Round #528 (Div. 1, based on Technocup 2019 Elimination Round 4)B - Minimum Diameter Tree

题目(假图论):
http://codeforces.com/contest/1086/problem/B

 

分析:

Codeforces Round #528 (Div. 1, based on Technocup 2019 Elimination Round 4)B - Minimum Diameter Tree

https://www.cnblogs.com/dybala21/p/10171450.html

 

比如在这幅图中:

Codeforces Round #528 (Div. 1, based on Technocup 2019 Elimination Round 4)B - Minimum Diameter Tree

   实际上我们是让链接任意两条叶子结点的路径的长度都相等,即,平均s到这所有距离叶子结点最近的边上去(长度记为L),(来自均值不等式的平均最小思想)。中间路径设为了0.按照正常思维,应该是每条路径都平均分摊是最好的,但是在这里,如果要把(假如说是0.2)分到2<->5这条路上,那么看似2->1,2->3, 5->6, 5->4会少一些。但是如果我们把这0.2平均分到这四条距离叶子结点最近的边上,那么每条路的最短距离都减小了。又因为中间路径长度设成0,所以最后任意两个叶子结点的距离就是2*L。

 

代码:

在代码中要注意的是,建图的时候,每个叶子结点的序号的输入只会出现一次!!!
 

//2
#include<stdio.h>
#include<string.h>
#define MAXN 200010

int Leaf[MAXN];

int main()
{
    int i;
    int n,s;
    int u,v;
    int cnt;

    scanf("%d%d",&n,&s);
    for(i=1;i<=n-1;i++)
    {
        scanf("%d%d",&u,&v);
        Leaf[u]++;
        Leaf[v]++;
    }
    cnt=0;
    for(i=1;i<=n;i++)
        if(Leaf[i]==1)
            cnt++;
    printf("%.18lf\n",s*1.0/cnt*2);
    return 0;
}