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 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117
| #define MAXN 200005 #define MAXM 1000005 int n, m; vector<int> G[MAXN];
struct Euler_Tour { int tt = 0; int in[MAXN], out[MAXN], d[MAXN], sz[MAXN]; int arr[25][MAXN];
bool isAnc(int i, int j) { return (in[i] <= in[j] && out[i] >= out[j]); }
void init() { out[0] = INF; }
void dfs(int i, int dep) { in[i] = ++tt; d[i] = dep; for (int e: G[i]) { if (!in[e]) { arr[0][e] = i; dfs(e, dep + 1); sz[i] += sz[e]; } } out[i] = ++tt; sz[i]++; }
void buildST() { for (int i = 1; i <= __lg(n); i++) { for (int j = 1; j <= n; j++) { arr[i][j] = arr[i - 1][arr[i - 1][j]]; } } } } ET;
struct LCA { int find(int a, int b) { if (ET.in[a] > ET.in[b]) swap(a, b);
if (ET.isAnc(a, b)) { return a; }
for (int i = 20; i >= 0; i--) { if (!ET.isAnc(ET.arr[i][a], b)) { a = ET.arr[i][a]; } }
return ET.arr[0][a]; }
int mv(int a, int dis) { for (int i = 20; i >= 0; i--) { if (dis >= (1 << i)) { a = ET.arr[i][a]; dis -= (1 << i); } } return a; } } LCA;
void sol() { cin >> n; for (int i = 1, a, b; i < n; i++) { cin >> a >> b; G[a].pb(b); G[b].pb(a); }
ET.init(); ET.dfs(1, 1); ET.buildST();
cin >> m; while (m--) { int a, b; cin >> a >> b;
if (a == b) { cout << n << endl; continue; }
int lca = LCA.find(a, b); int disa = ET.d[a] - ET.d[lca]; int disb = ET.d[b] - ET.d[lca];
if ((disa + disb) % 2 == 0) { int mid = LCA.mv((disa > disb) ? a : b, (disa + disb) / 2); int ans = n;
if (ET.isAnc(mid, a)) ans -= ET.sz[LCA.mv(a, (disa + disb) / 2 - 1)]; else ans -= n - ET.sz[mid];
if (ET.isAnc(mid, b)) ans -= ET.sz[LCA.mv(b, (disa + disb) / 2 - 1)]; else ans -= n - ET.sz[mid]; cout << ans << endl; } else { cout << 0 << endl; } } }
|