poj 3107 Godfather 求树的重心【树形dp】

poj 3107 Godfather 

poj 1655差不多,那道会了这个也就差不多了。

题意:从小到大输出树的重心。

题会卡stl,要用邻接表存树。。。。。

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cstring>
 4 #include<algorithm>
 5 using namespace std;
 6 const int maxn = 50006;
 7 const int INF = 1 << 30;
 8 int head[maxn];
 9 int son[maxn], ans[maxn];
10 bool vis[maxn];
11 int n, siz, cnt, tot;
12 struct Edge
13 {
14     int to, next;
15 };
16 Edge edge[maxn * 2];
17 
18 void Init()
19 {
20     memset(vis, 0, sizeof(vis));
21     memset(head, -1, sizeof(head));
22     siz = INF;
23     cnt = tot = 0;
24 }
25 
26 
27 void add(int u, int v)
28 {
29     edge[cnt].to = v;
30     edge[cnt].next = head[u];
31     head[u] = cnt++;
32 }
33 
34 void dfs(int u)
35 {
36     vis[u] = 1;
37     son[u] = 1;
38     int tmp = 0;
39     for (int i = head[u]; i != -1; i = edge[i].next)
40     {
41         int v = edge[i].to;
42         if (!vis[v]) {
43             dfs(v);
44             son[u] += son[v];
45             tmp = max(tmp, son[v]);
46         }
47     }
48     tmp = max(tmp, n - son[u]);
49     if (tmp == siz) {
50         ans[tot++] = u;
51     }
52     else if (tmp<siz) {
53         tot = 0;
54         ans[tot++] = u;
55         siz = tmp;
56     }
57 }
58 
59 int main()
60 {
61     while (scanf("%d", &n) == 1)
62     {
63         Init();
64         for (int i = 1; i < n; i++) {
65             int u, v;
66             scanf("%d%d", &u, &v);
67             add(u, v);
68             add(v, u);
69         }
70         dfs(1);
71         sort(ans, ans + tot);
72         for (int i = 0; i<tot; i++) {
73             printf("%d ", ans[i]);
74         }
75         printf("
");
76     }
77     return 0;
78 }
原文地址:https://www.cnblogs.com/zxhyxiao/p/7784591.html