wenbao与LCA

 

 

 ----------------------------------------------------------------------------------------------------------------

 dfs+st(在线处理)

 

模板

 

  1 const int maxn = 3e5+10;
  2 int n;
  3 
  4 struct adjs {
  5     int to, next;
  6 } ad[maxn<<1];
  7 
  8 int head[maxn], adcnt;
  9 
 10 void adjs_init() {
 11     for(int i = 1; i <= n; i++) head[i] = -1, vis[i] = false;
 12     adcnt = 0;
 13 }
 14 
 15 void add_edge(int a, int b) {
 16     ad[adcnt].next = head[a];
 17     ad[adcnt].to = b;
 18     head[a] = adcnt++;
 19 }
 20 
 21 int S;
 22 int a[maxn];
 23 
 24 int dep[maxn];
 25 
 26 int dfs_pre[maxn*2];
 27 int pw[maxn*2];
 28 int G[maxn];
 29 int dfs_clk;
 30 
 31 void init() {
 32     pw[1] = 0;
 33     for(int i = 2; i < maxn*2; i++) pw[i] = pw[i-1] + !(i&(i-1));
 34 }
 35 
 36 struct ST {
 37     int N;
 38     int T[23][maxn*2];
 39 
 40     void init(int _N, int *arr) {
 41         N = _N;
 42         for(int i = 1; i <= N; i++) T[0][i] = arr[i];
 43     }
 44 
 45     inline int _max(int x,int y) {
 46         if(dep[x] < dep[y]) return x;
 47         else return y;
 48     }
 49 
 50     void update() {
 51         for(int i = 1; i <= pw[N]; i++) {
 52             for(int j = 1; j+(1<<i)-1 <= N; j++) {
 53                 T[i][j] = _max(T[i-1][j], T[i-1][j+(1<<(i-1))]);
 54             }
 55         }
 56     }
 57 
 58     int LCA(int x, int y) {
 59         if(x > y) swap(x, y);
 60         int p = pw[y-x+1];
 61         return _max(T[p][x], T[p][y-(1<<p)+1]);
 62     }
 63 } st;
 64 
 65 
 66 void dfs(int u, int fa) {
 67     // cout << u << "***" << fa << endl;
 68     dep[u] = dep[fa] + 1;
 69     dfs_pre[++dfs_clk] = u;
 70     G[u] = dfs_clk;
 71     for(int i = head[u]; ~i; i = ad[i].next) {
 72         int v = ad[i].to;
 73         if(v == fa) continue;
 74         dfs(v, u);
 75         dfs_pre[++dfs_clk] = u;
 76     }
 77 }
 78 
 79 int dis(int x, int y) {
 80     int lca = st.LCA(G[x], G[y]);
 81     return dep[x] + dep[y] - dep[lca] - dep[lca];
 82 }
 83 
 84 int main() {
 85     init();
 86     scanf("%d", &n);
 87     for(int i = 1; i < n; ++i) {
 88         scanf("%d%d", &x, &y);
 89         add_edge(x, y), add_edge(y, x);
 90     }
 91     dfs_clk = 0;
 92     dfs(1, 0);
 93     // cout<<"**"<<endl;
 94     st.init(dfs_clk, dfs_pre);
 95     st.update();
 96     scanf("%d", &q);
 97     while(q--) {
 98         scanf("%d%d", &x, &y);
 99         printf("%d\n", dis(x, y));
100     }
101 }

 

 

---------------

 http://poj.org/problem?id=1330

求LCA

 

  1 #include <iostream>
  2 #include <algorithm>
  3 using namespace std;
  4 
  5 const int maxn = 3e5+10;
  6 int n;
  7 bool vis[maxn];
  8 
  9 struct adjs {
 10     int to, next;
 11 } ad[maxn<<1];
 12 
 13 int head[maxn], adcnt;
 14 
 15 void adjs_init() {
 16     for(int i = 1; i <= n; i++) head[i] = -1, vis[i] = false;
 17     adcnt = 0;
 18 }
 19 
 20 void add_edge(int a, int b) {
 21     ad[adcnt].next = head[a];
 22     ad[adcnt].to = b;
 23     head[a] = adcnt++;
 24 }
 25 
 26 int S;
 27 int a[maxn];
 28 
 29 int dep[maxn];
 30 
 31 int dfs_pre[maxn*2];
 32 int pw[maxn*2];
 33 int G[maxn];
 34 int dfs_clk;
 35 
 36 void init(){
 37     pw[1]=0;
 38     for(int i=2; i<maxn*2; i++) pw[i] = pw[i-1] + !(i&(i-1));
 39 }
 40 
 41 struct ST {
 42     int N;
 43     int T[23][maxn*2];
 44 
 45     void init(int _N, int *arr) {
 46         N=_N;
 47         for(int i = 1; i <= N; i++) T[0][i] = arr[i];
 48     }
 49 
 50     inline int _max(int x,int y) {
 51         if(dep[x] < dep[y]) return x;
 52         else return y;
 53     }
 54 
 55     void update() {
 56         for(int i = 1; i <= pw[N]; i++) {
 57             for(int j = 1; j+(1<<i)-1 <= N; j++) {
 58                 T[i][j] = _max(T[i-1][j], T[i-1][j+(1<<(i-1))]);
 59             }
 60         }
 61     }
 62 
 63     int LCA(int x, int y) {
 64         if(x > y) swap(x, y);
 65         int p = pw[y-x+1];
 66         return _max(T[p][x], T[p][y-(1<<p)+1]);
 67     }
 68 } st;
 69 
 70 
 71 void dfs(int u, int fa) {
 72     dep[u] = dep[fa] + 1;
 73     dfs_pre[++dfs_clk] = u;
 74     G[u] = dfs_clk;
 75     for(int i = head[u]; ~i; i = ad[i].next) {
 76         int v = ad[i].to;
 77         if(v == fa) continue;
 78         dfs(v, u);
 79         dfs_pre[++dfs_clk] = u;
 80     }
 81 }
 82 
 83 
 84 int main() {
 85     init();
 86     int t;
 87     scanf("%d", &t);
 88     while(t--) {
 89         scanf("%d", &n);
 90         adjs_init();
 91         int x, y;
 92         for(int i = 1; i < n; i++) {
 93             scanf("%d%d", &x, &y);
 94             add_edge(x,y);
 95             add_edge(y,x);
 96             vis[y] = true;
 97         }
 98         int id;
 99         for(int i = 1; i <= n; ++i){
100             if(!vis[i]){
101                 id = i;
102                 break;
103             }
104         }
105         dfs_clk = 0;
106         dfs(id, 0);
107         //cout<<"**"<<endl;
108         st.init(dfs_clk, dfs_pre);
109         st.update();
110         scanf("%d%d", &x, &y);
111         printf("%d\n", st.LCA(G[x], G[y]));
112     }
113 }

 

 

 

------------------------------------

求LCA 

 

http://hihocoder.com/problemset/problem/1069

 

  1 #include <iostream>
  2 #include <algorithm>
  3 #include <map>
  4 #include <string>
  5 #include <string.h>
  6 using namespace std;
  7 
  8 const int maxn = 1e5+10;
  9 map<string, int> m;
 10 string mm[maxn];
 11 int n;
 12 struct adjs {
 13     int to, next;
 14 } ad[maxn<<1];
 15 int head[maxn], adcnt;
 16 
 17 bool vis[maxn];
 18 
 19 void adjs_init() {
 20     for(int i = 1; i < maxn; i++) head[i] = -1, vis[i] = false;
 21     adcnt = 0;
 22 }
 23 void add_edge(int a, int b) {
 24     ad[adcnt].next = head[a];
 25     ad[adcnt].to = b;
 26     head[a] = adcnt++;
 27 }
 28 
 29 int S;
 30 int a[maxn];
 31 
 32 int dep[maxn];
 33 
 34 int dfs_pre[maxn*2];
 35 int pw[maxn*2];
 36 int G[maxn];
 37 int dfs_clk;
 38 
 39 void init() {
 40     pw[1]=0;
 41     for(int i=2; i<maxn*2; i++) pw[i] = pw[i-1] + !(i&(i-1));
 42 }
 43 
 44 struct ST {
 45     int N;
 46     int T[23][maxn*2];
 47 
 48     void init(int _N, int *arr) {
 49         N=_N;
 50         for(int i = 1; i <= N; i++) T[0][i] = arr[i];
 51     }
 52 
 53     inline int _max(int x,int y) {
 54         if(dep[x] < dep[y]) return x;
 55         else return y;
 56     }
 57 
 58     void update() {
 59         for(int i = 1; i <= pw[N]; i++) {
 60             for(int j = 1; j+(1<<i)-1 <= N; j++) {
 61                 T[i][j] = _max(T[i-1][j], T[i-1][j+(1<<(i-1))]);
 62             }
 63         }
 64     }
 65 
 66     int LCA(int x, int y) {
 67         if(x > y) swap(x, y);
 68         int p = pw[y-x+1];
 69         return _max(T[p][x], T[p][y-(1<<p)+1]);
 70     }
 71 } st;
 72 
 73 
 74 void dfs(int u, int fa) {
 75     dep[u] = dep[fa] + 1;
 76     dfs_pre[++dfs_clk] = u;
 77     G[u] = dfs_clk;
 78     for(int i = head[u]; ~i; i = ad[i].next) {
 79         int v = ad[i].to;
 80         if(v == fa) continue;
 81         dfs(v, u);
 82         dfs_pre[++dfs_clk] = u;
 83     }
 84 }
 85 
 86 char x[111], y[111];
 87 int main() {
 88     init();
 89     int t;
 90     while(~scanf("%d", &n)) {
 91         m.clear();
 92         adjs_init();
 93         int num = 1;
 94         for(int i = 0; i < n; i++) {
 95             scanf("%s%s", x, y);
 96             if(!m[x]) mm[num] = x, m[x] = num++;
 97             if(!m[y]) mm[num] = y, m[y] = num++;
 98             add_edge(m[x],m[y]);
 99             add_edge(m[y],m[x]);
100             vis[m[y]] = true;
101         }
102         int id;
103         for(int i = 1; i <= n; ++i) {
104             if(!vis[i]) {
105                 id = i;
106                 break;
107             }
108         }
109         dfs_clk = 0;
110         dfs(id, 0);
111         st.init(dfs_clk, dfs_pre);
112         st.update();
113         int t;
114         scanf("%d", &t);
115         for(int i = 0; i < t; ++i) {
116             scanf("%s%s", x, y);
117             printf("%s\n", mm[st.LCA(G[m[x]], G[m[y]])].c_str());
118         }
119     }
120 }

 

 

 --------------------------

 

 

http://codeforces.com/contest/832/problem/D

 

  1 #include <iostream>
  2 #include <algorithm>
  3 using namespace std;
  4 
  5 const int maxn = 3e5+10;
  6 int n, q;
  7 struct adjs {
  8     int to, next;
  9 } ad[maxn<<1];
 10 int head[maxn], adcnt;
 11 
 12 
 13 void adjs_init() {
 14     for(int i = 1; i <= n; i++) head[i] = -1;
 15     adcnt = 0;
 16 }
 17 void add_edge(int a, int b) {
 18     ad[adcnt].next = head[a];
 19     ad[adcnt].to = b;
 20     head[a] = adcnt++;
 21 }
 22 
 23 int S;
 24 int a[maxn];
 25 
 26 int dep[maxn];
 27 
 28 int dfs_pre[maxn*2];
 29 int pw[maxn*2];
 30 int G[maxn];
 31 int dfs_clk;
 32 
 33 void init() {
 34     pw[1]=0;
 35     for(int i=2; i<maxn*2; i++) pw[i] = pw[i-1] + !(i&(i-1));
 36 }
 37 
 38 struct ST {
 39     int N;
 40     int T[23][maxn*2];
 41 
 42     void init(int _N, int *arr) {
 43         N=_N;
 44         for(int i = 1; i <= N; i++) T[0][i] = arr[i];
 45     }
 46 
 47     inline int _max(int x,int y) {
 48         if(dep[x] < dep[y]) return x;
 49         else return y;
 50     }
 51 
 52     void update() {
 53         for(int i = 1; i <= pw[N]; i++) {
 54             for(int j = 1; j+(1<<i)-1 <= N; j++) {
 55                 T[i][j] = _max(T[i-1][j], T[i-1][j+(1<<(i-1))]);
 56             }
 57         }
 58     }
 59 
 60     int LCA(int x, int y) {
 61         if(x > y) swap(x, y);
 62         int p = pw[y-x+1];
 63         return _max(T[p][x], T[p][y-(1<<p)+1]);
 64     }
 65 } st;
 66 
 67 
 68 void dfs(int u, int fa) {
 69     //cout<<u<<"**"<<fa<<endl;
 70     dep[u] = dep[fa] + 1;
 71     dfs_pre[++dfs_clk] = u;
 72     G[u] = dfs_clk;
 73     for(int i = head[u]; ~i; i = ad[i].next) {
 74         int v = ad[i].to;
 75         if(v == fa) continue;
 76         dfs(v, u);
 77         dfs_pre[++dfs_clk] = u;
 78     }
 79 }
 80 
 81 int dis(int x, int y) {
 82     int lca = st.LCA(G[x], G[y]);
 83     return dep[x] + dep[y] - dep[lca] - dep[lca];
 84 }
 85 
 86 int main() {
 87     init();
 88     scanf("%d%d", &n, &q);
 89     adjs_init();
 90     int x;
 91     for(int i = 2; i <= n; ++i) {
 92         scanf("%d", &x);
 93         add_edge(x, i), add_edge(i, x);
 94     }
 95     dfs_clk = 0;
 96     //cout<<"***"<<endl;
 97     dfs(1, 0);
 98     st.init(dfs_clk, dfs_pre);
 99     st.update();
100     while(q--) {
101         int a, b, c;
102         scanf("%d%d%d", &a, &b, &c);
103         int ab = dis(a, b), ac = dis(a, c), bc = dis(b, c);
104         printf("%d\n", (ab+ac+bc)/2-min(min(ab,bc),ac)+1);
105     }
106     return 0;
107 }

 

 

 ----------------------------------------------------------------------------------------------------------------

倍增(在线处理)

 

http://poj.org/problem?id=1330

 

 1 #include <iostream>
 2 #include <vector>
 3 #include <string.h>
 4 using namespace std;
 5 const int maxn = 10009;
 6 vector<int> v[maxn];
 7 int fa[maxn], f[21][maxn], dep[maxn], nu[maxn], t, n, root;
 8 void d(int x){
 9     f[0][x] = fa[x];
10     for(int i = 1; i <= 20; ++i){
11         f[i][x] = f[i-1][f[i-1][x]];
12     }
13     for(int i = 0; i < v[x].size(); ++i){
14         int xx = v[x][i];
15         if(xx != fa[x]){
16             fa[xx] = x, dep[xx] = dep[x] + 1, d(xx);
17         }
18     }
19 }
20 int q(int x, int y){
21     if(dep[x] < dep[y]) swap(x, y);
22     for(int i = 20; i >= 0; --i){
23         if(dep[y] <= dep[f[i][x]]){
24             x = f[i][x];
25         }
26     }
27     if(x == y) return x;
28     for(int i = 20; i >= 0; --i){
29         if(f[i][x] != f[i][y]){
30             x = f[i][x], y = f[i][y];
31         }
32     }
33     return f[0][x];
34 }
35 void init(){
36     root = 0;
37     memset(f, 0, sizeof(f));
38     for(int i = 0; i <= n; ++i){
39         v[i].clear(), dep[i] = 0, fa[i] = 0, nu[i] = 0;
40     }
41 }
42 int main(){
43     scanf("%d", &t);
44     while(t--){
45         scanf("%d", &n);
46         int x, y;
47         init();
48         for(int i = 1; i < n; ++i){
49             scanf("%d%d", &x, &y);
50             v[x].push_back(y), v[y].push_back(x);
51             nu[y]++;
52         }
53         while(nu[++root]);
54         fa[root] = root, dep[root] = 0;
55         d(root);
56         scanf("%d%d", &x, &y);
57         printf("%d\n", q(x, y));
58     }
59     return 0;
60 }

 

------------------------------------------

 

http://codeforces.com/contest/832/problem/D

 

 1 #include <iostream>
 2 #include <string.h>
 3 #include <vector>
 4 using namespace std;
 5 const int maxn = 1e5+10;
 6 vector<int> v[maxn];
 7 int f[21][maxn], fa[maxn], dep[maxn];
 8 void d(int x){
 9     f[0][x] = fa[x];
10     for(int i = 1; i <= 20; ++i){
11         f[i][x] = f[i-1][f[i-1][x]];
12     }
13     for(int i = 0; i < v[x].size(); ++i){
14         int xx = v[x][i];
15         if(xx != fa[x]){
16             fa[xx] = x, dep[xx] = dep[x] + 1;
17             d(xx);
18         }
19     }
20 }
21 int q(int x, int y){
22     int sum = dep[x] + dep[y], xx;
23     if(dep[x] < dep[y]) swap(x, y);
24     for(int i = 20; i >= 0; --i){
25         if(dep[y] <= dep[f[i][x]]) x = f[i][x];
26     }
27     if(x == y) xx = x;
28     else{
29         for(int i = 20; i >= 0; --i){
30             if(f[i][x] != f[i][y]){
31                 x = f[i][x], y = f[i][y];
32             }
33         }
34         xx = f[0][x];
35     }
36     return sum - 2*dep[xx];
37 }
38 int main(){
39     int n, m, x;
40     scanf("%d%d", &n, &m);
41     for(int i = 2; i <= n; ++i){
42         scanf("%d", &x);
43         v[i].push_back(x), v[x].push_back(i);
44     }
45     fa[1] = 1, dep[1] = 0;
46     d(1);
47     while(m--){
48         int a, b, c;
49         scanf("%d%d%d", &a, &b, &c);
50         int ab = q(a, b), ac = q(a, c), bc = q(b, c);
51         printf("%d\n", (ab+ac+bc)/2-min(min(ab, ac), bc)+1);
52     }
53     return 0;
54 }

 

 

 ----------------------------------------------------------------------------------------------------------------

 

tarjan(离线处理)

 

----------------------------

http://codevs.cn/problem/2370/

 

 1 #include <iostream>
 2 #include <string.h>
 3 #include <vector>
 4 #include <stdio.h>
 5 using namespace std;
 6 const int maxn = 50000;
 7 int t, n, m, f[maxn], dis[maxn], sum[75009];
 8 bool vis[maxn];
 9 vector<int> v[maxn], w[maxn], q[maxn], num[maxn];
10 void init(){
11     for(int i = 0; i <= n; ++i){
12         v[i].clear(), w[i].clear(), q[i].clear(), num[i].clear();
13         f[i] = i, vis[i] = false;
14     }
15 }
16 int F(int x){
17     return f[x] == x ? x : f[x] = F(f[x]);
18 }
19 void uni(int x, int y){
20     int xx = F(x), yy = F(y);
21     if(xx != yy) f[yy] = xx;
22 }
23 void tr(int x, int cnt){
24     vis[x] = true, dis[x] = cnt;
25     for(int i = 0; i < v[x].size(); ++i){
26         int xx = v[x][i];
27         if(vis[xx]) continue;
28         tr(xx, cnt+w[x][i]);
29         uni(x, xx);
30     }
31     for(int i = 0; i < q[x].size(); ++i){
32         int xx = q[x][i];
33         if(vis[xx]){
34             sum[num[x][i]] = dis[x] + dis[xx] - 2*dis[F(xx)];
35         }
36     }
37 }
38 int main(){
39     scanf("%d", &n);
40     int x, y, ww;
41     init();
42     for(int i = 1; i < n; ++i){
43         scanf("%d%d%d", &x, &y, &ww);
44         v[x].push_back(y);
45         w[x].push_back(ww);
46         v[y].push_back(x);
47         w[y].push_back(ww);
48     }
49     scanf("%d", &m);
50     for(int i = 0; i < m; ++i){
51         scanf("%d%d", &x, &y);
52         q[x].push_back(y);
53         q[y].push_back(x);
54         num[x].push_back(i);
55         num[y].push_back(i);
56     }
57     tr(1, 0);
58     for(int i = 0; i < m; ++i){
59         printf("%d\n", sum[i]);
60     }
61     return 0;
62 }

 

 

---------------------

http://acm.hdu.edu.cn/showproblem.php?pid=2586 

 

 1 #include <iostream>
 2 #include <string.h>
 3 #include <vector>
 4 using namespace std;
 5 const int maxn = 40009;
 6 int t, n, m, f[maxn], dis[maxn], sum[maxn];
 7 bool vis[maxn];
 8 vector<int> v[maxn], w[maxn], q[maxn], num[maxn];
 9 void init(){
10     for(int i = 0; i <= n; ++i){
11         v[i].clear(), w[i].clear(), q[i].clear(), num[i].clear();
12         f[i] = i, vis[i] = false;
13     }
14 }
15 int F(int x){
16     return f[x] == x ? x : f[x] = F(f[x]);
17 }
18 void uni(int x, int y){
19     int xx = F(x), yy = F(y);
20     if(xx != yy) f[yy] = xx;
21 }
22 void tr(int x, int cnt){
23     vis[x] = true, dis[x] = cnt;
24     for(int i = 0; i < v[x].size(); ++i){
25         int xx = v[x][i];
26         if(vis[xx]) continue;
27         tr(xx, cnt+w[x][i]);
28         uni(x, xx);
29     }
30     for(int i = 0; i < q[x].size(); ++i){
31         int xx = q[x][i];
32         if(vis[xx]){
33             sum[num[x][i]] = dis[x] + dis[xx] - 2*dis[F(xx)];
34         }
35     }
36 }
37 int main(){
38     scanf("%d", &t);
39     while(t--){
40         scanf("%d%d", &n, &m);
41         int x, y, ww;
42         init();
43         for(int i = 1; i < n; ++i){
44             scanf("%d%d%d", &x, &y, &ww);
45             v[x].push_back(y);
46             w[x].push_back(ww);
47             v[y].push_back(x);
48             w[y].push_back(ww);
49         }
50         for(int i = 0; i < m; ++i){
51             scanf("%d%d", &x, &y);
52             q[x].push_back(y);
53             q[y].push_back(x);
54             num[x].push_back(i);
55             num[y].push_back(i);
56         }
57         tr(1, 0);
58         for(int i = 0; i < m; ++i){
59             printf("%d\n", sum[i]);
60         }
61     }
62     return 0;
63 }

 

 -----------------------------------------------------------

 

https://www.nowcoder.com/acm/contest/15/C

 

可以证明此题可以转化为求虚数的最长直径的一半(向上取整)

 

  1 #include <iostream>
  2 #include <algorithm>
  3 using namespace std;
  4 
  5 const int maxn = 3e5+10;
  6 int n;
  7 struct adjs {
  8     int to, next;
  9 } ad[maxn<<1];
 10 int head[maxn], adcnt;
 11 void adjs_init() {
 12     for(int i = 1; i <= n; i++) head[i] = -1;
 13     adcnt = 0;
 14 }
 15 void add_edge(int a, int b) {
 16     ad[adcnt].next = head[a];
 17     ad[adcnt].to = b;
 18     head[a] = adcnt++;
 19 }
 20 
 21 int S;
 22 int a[maxn];
 23 
 24 int dep[maxn];
 25 
 26 int dfs_pre[maxn*2];
 27 int pw[maxn*2];
 28 int G[maxn];
 29 int dfs_clk;
 30 
 31 void init(){
 32     pw[1]=0;
 33     for(int i=2; i<maxn*2; i++) pw[i] = pw[i-1] + !(i&(i-1));
 34 }
 35 
 36 struct ST {
 37     int N;
 38     int T[23][maxn*2];
 39 
 40     void init(int _N, int *arr) {
 41         N=_N;
 42         for(int i = 1; i <= N; i++) T[0][i] = arr[i];
 43     }
 44 
 45     inline int _max(int x,int y) {
 46         if(dep[x] < dep[y]) return x;
 47         else return y;
 48     }
 49 
 50     void update() {
 51         for(int i = 1; i <= pw[N]; i++) {
 52             for(int j = 1; j+(1<<i)-1 <= N; j++) {
 53                 T[i][j] = _max(T[i-1][j], T[i-1][j+(1<<(i-1))]);
 54             }
 55         }
 56     }
 57 
 58     int LCA(int x, int y) {
 59         if(x > y) swap(x, y);
 60         int p = pw[y-x+1];
 61         return _max(T[p][x], T[p][y-(1<<p)+1]);
 62     }
 63 } st;
 64 
 65 
 66 void dfs(int u, int fa) {
 67     dep[u] = dep[fa]+1;
 68     dfs_pre[++dfs_clk] = u;
 69     G[u] = dfs_clk;
 70 
 71     for(int i = head[u]; ~i; i = ad[i].next) {
 72         int v = ad[i].to;
 73         if(v == fa) continue;
 74         dfs(v, u);
 75         dfs_pre[++dfs_clk] = u;
 76     }
 77 }
 78 
 79 
 80 inline int CMP(const int x,const int y) {
 81     return dep[x] > dep[y];
 82 }
 83 
 84 int main() {
 85     init();
 86     while(~scanf("%d",&n)) {
 87         adjs_init();
 88         for(int i = 1; i < n; i++) {
 89             int x, y;
 90             scanf("%d", &x), scanf("%d", &y);
 91             add_edge(x,y);
 92             add_edge(y,x);
 93         }
 94         dfs_clk = 0;
 95         dfs(1, 0);
 96         st.init(dfs_clk, dfs_pre);
 97         st.update();
 98         int Q;
 99         scanf("%d", &Q);
100         while(Q--) {
101             scanf("%d", &S);
102             for(int i = 0; i < S; i++) scanf("%d", &a[i]);
103             sort(a, a+S, CMP);
104             int ans = 0, ntp, dist;
105             for(int i = 1; i < S; i++) {
106                 ntp = st.LCA(G[a[0]],G[a[i]]);
107                 dist = dep[a[0]] + dep[a[i]] - dep[ntp] - dep[ntp];
108                 dist = (dist+1)>>1;
109                 if(ans < dist) ans = dist;
110             }
111             printf("%d\n", ans);
112         }
113     }
114 }

 

 

------------------------------------------------------------

 

 

只有不断学习才能进步!

 

posted @ 2018-04-14 13:52  wenbao  阅读(137)  评论(0编辑  收藏  举报