1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73
| #include <bits/stdc++.h> #define LOG 20 #define MAX_N 1000000 #define INF 0x3f3f3f3f using namespace std; typedef long long lnt; template <class T> inline void read(T &x) { x = 0; int c = getchar(), f = 1; for (; !isdigit(c); c = getchar()) if (c == 45) f = -1; for (; isdigit(c); c = getchar()) (x *= 10) += f*(c-'0'); } int n, m, q, fa[MAX_N+5][LOG+1]; int ind, dfn[MAX_N+5], dep[MAX_N+5]; vector <int> G[MAX_N+5], T[MAX_N+5]; int sz[MAX_N+5]; bool mrk[MAX_N+5]; vector <int> p; int s[MAX_N+5], tp; lnt tot; int mi, mx, f[MAX_N+5], g[MAX_N+5]; bool cmp (const int &a, const int &b) {return dfn[a] < dfn[b];} void DFS(int u) { dfn[u] = ++ind, dep[u] = dep[fa[u][0]]+1; for (int i = 1; i <= LOG; i++) fa[u][i] = fa[fa[u][i-1]][i-1]; for (int i = 0, v; i < (int)G[u].size(); i++) if ((v = G[u][i]) ^ fa[u][0]) fa[v][0] = u, DFS(v); } int LCA(int u, int v) { if (dep[u] < dep[v]) swap(u, v); for (int i = LOG; ~i; i--) if (dep[u]-(1<<i) >= dep[v]) u = fa[u][i]; if (u == v) return u; for (int i = LOG; ~i; i--) if (fa[u][i] ^ fa[v][i]) u = fa[u][i], v = fa[v][i]; return fa[u][0]; } void DP(int u) { sz[u] = mrk[u], f[u] = INF, g[u] = 0; for (int i = 0; i < (int)T[u].size(); i++) { int v = T[u][i], l = dep[v]-dep[u]; DP(v), sz[u] += sz[v], tot += 1LL*sz[v]*(m-sz[v])*l; mi = min(mi, f[u]+f[v]+l), mx = max(mx, g[u]+g[v]+l); f[u] = min(f[u], f[v]+l), g[u] = max(g[u], g[v]+l); } if (mrk[u]) mi = min(mi, f[u]), mx = max(mx, g[u]); if (mrk[u]) f[u] = 0; T[u].clear(), mrk[u] = false; } int main() { read(n); for (int i = 1, u, v; i < n; i++) read(u), read(v), G[u].push_back(v), G[v].push_back(u); DFS(1), read(q); while (q--) { read(m), p.clear(), tp = 0; for (int i = 0, x; i < m; i++) read(x), p.push_back(x), mrk[x] = true; sort(p.begin(), p.end(), cmp); for (int i = 0; i < m; i++) if (!tp) s[++tp] = p[i]; else { int lca = LCA(p[i], s[tp]); while (dfn[lca] < dfn[s[tp]]) if (dfn[lca] >= dfn[s[tp-1]]) { T[lca].push_back(s[tp]); if (s[--tp] ^ lca) s[++tp] = lca; } else T[s[tp-1]].push_back(s[tp]), tp--; s[++tp] = p[i]; } while (tp > 1) T[s[tp-1]].push_back(s[tp]), tp--; mi = INF, mx = 0, tot = 0; DP(s[tp]); printf("%lld %d %d\n", tot, mi, mx); } return 0; }
|