(树的重心)POJ 1655 Balancing Act
题目链接:POJ 1655
题目大意:
就是找重心,遇到两个重心,输出编号小的。
参考代码:
1 // 树的重心 2 // POJ 1655 3 #include <iostream> 4 #include <cstdio> 5 #include <cstring> 6 #include <cmath> 7 #include <algorithm> 8 #include <queue> 9 #include <vector> 10 #include <stack> 11 #define N 40010 12 #define ll long long 13 using namespace std; 14 int t; 15 int n; 16 int u,v; 17 int cnt; 18 int balance,node; // balance是重心最大子树的节点数,node为重心编号 19 int head[N],nxt[N],to[N],son[N]; 20 inline int read() 21 { 22 int x = 0, y = 1; char c = getchar(); 23 while(c < '0' || c > '9') {if(c == '-') y = -1; c = getchar();} 24 while(c >= '0' && c <= '9') x = x*10+c-'0', c = getchar(); 25 return x*y; 26 } 27 void add(int u, int v) 28 { 29 nxt[++cnt] = head[u]; 30 head[u] = cnt; 31 to[cnt] = v; 32 } 33 void dfs(int u, int fa) 34 { 35 son[u] = 1; 36 int w = 0; // 注意此处不能定义为全局变量 37 for(int i = head[u]; ~i; i = nxt[i]) 38 { 39 int v = to[i]; 40 if(v != fa) 41 { 42 dfs(v,u); 43 son[u] += son[v]; 44 w = max(w,son[v]); 45 } 46 } 47 w = max(w,n-son[u]); // 向上的节点数 48 if(w < balance) 49 { 50 balance = w; 51 node = u; 52 } else if(w == balance) // 相同,取编号小的 53 node = min(u,node); 54 } 55 void init() 56 { 57 cnt = -1; 58 balance = N+10; // 赋值为较大值 59 memset(head,-1,sizeof(head)); 60 memset(son,0,sizeof(son)); 61 } 62 int main() 63 { 64 t = read(); 65 while(t--) 66 { 67 init(); 68 n = read(); 69 for(int i = 0; i < n-1; i++) 70 { 71 u = read(); 72 v = read(); 73 add(u,v); 74 add(v,u); 75 } 76 dfs(1,0); 77 printf("%d %d\n",node,balance); 78 } 79 return 0; 80 }

浙公网安备 33010602011771号