码迷,mamicode.com
首页 > 其他好文 > 详细

poj1655 Balancing Act(找树的重心)

时间:2017-12-17 11:04:03      阅读:89      评论:0      收藏:0      [点我收藏+]

标签:http   tin   相同   部分   style   get   clu   namespace   target   

Balancing Act

 POJ - 1655 

题意:给定一棵树,求树的重心的编号以及重心删除后得到的最大子树的节点个数size,如果size相同就选取编号最小的.

/*
    找树的重心可以用树形dp或者dfs,这里我用的dfs
    基本方法就是随便设定一个根节点,然后找出这个节点的子树大小(包括这个节点),然后总点数减去子树的大小就是向父亲节点走去的点数,使这几部分的最大值最小
*/
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#define maxn 20010
using namespace std;
int T,n,head[maxn],num,root,son[maxn],f[maxn];
struct node{
    int to,pre;
}e[maxn*2];
void Insert(int from,int to){
    e[++num].to=to;
    e[num].pre=head[from];
    head[from]=num;
}
void getroot(int x,int fa){
    son[x]=1;
    for(int i=head[x];i;i=e[i].pre){
        int to=e[i].to;
        if(to==fa)continue;
        getroot(to,x);
        son[x]+=son[to];
        f[x]=max(f[x],son[to]);
    }
    f[x]=max(f[x],n-son[x]);
    if(f[x]<f[root])root=x;
}
int main(){
    scanf("%d",&T);
    while(T--){
        root=0;
        memset(f,0,sizeof(f));f[root]=0x7fffffff;
        memset(son,0,sizeof(son));
        memset(head,0,sizeof(head));num=0;
        memset(e,0,sizeof(e));
        scanf("%d",&n);
        int x,y;
        for(int i=1;i<n;i++){
            scanf("%d%d",&x,&y);
            Insert(x,y);Insert(y,x);
        }
        getroot(1,0);
        printf("%d %d\n",root,f[root]);
    }
}

 

 

poj1655 Balancing Act(找树的重心)

标签:http   tin   相同   部分   style   get   clu   namespace   target   

原文地址:http://www.cnblogs.com/thmyl/p/8051360.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!