洛谷P4211 LCA
题意:多次询问,每次求点的标号在[l, r]之间的所有点到点z的lca的深度。
解:看到这题有没有想到某一道很熟悉的题?紫妹和幽香是17岁的少女,喜欢可爱的东西......
显然这就是开店的超级无敌弱化版......直接套用做法就行了。
记得对"爱你一生一世"取模。(滑稽)
1 #include <cstdio> 2 #include <algorithm> 3 4 typedef long long LL; 5 const int N = 50010, M = 5000010; 6 7 struct Edge { 8 int nex, v; 9 }edge[N]; int tp; 10 11 int e[N], top[N], num, fa[N], siz[N], son[N], d[N], n, pos[N]; 12 LL sum[M]; 13 int rt[N], tot, ls[M], rs[M], tag[M]; 14 15 inline void adde(int x, int y) { 16 tp++; 17 edge[tp].v = y; 18 edge[tp].nex = e[x]; 19 e[x] = tp; 20 return; 21 } 22 23 void DFS1(int x) { // get siz fa son d 24 siz[x] = 1; 25 d[x] = d[fa[x]] + 1; 26 for(int i = e[x]; i; i = edge[i].nex) { 27 int y = edge[i].v; 28 fa[y] = x; 29 DFS1(y); 30 siz[x] += siz[y]; 31 if(siz[y] > siz[son[x]]) { 32 son[x] = y; 33 } 34 } 35 return; 36 } 37 38 void DFS2(int x, int f) { // get pos id top 39 top[x] = f; 40 pos[x] = ++num; 41 if(son[x]) { 42 DFS2(son[x], f); 43 } 44 for(int i = e[x]; i; i = edge[i].nex) { 45 int y = edge[i].v; 46 if(y == son[x]) { 47 continue; 48 } 49 DFS2(y, y); 50 } 51 return; 52 } 53 54 void add(int x, int &y, int L, int R, int l, int r) { 55 if(!y || x == y) { 56 y = ++tot; 57 sum[y] = sum[x]; 58 tag[y] = tag[x]; 59 ls[y] = ls[x]; 60 rs[y] = rs[x]; 61 } 62 sum[y] += std::min(R, r) - std::max(L, l) + 1; 63 if(L <= l && r <= R) { 64 tag[y]++; 65 return; 66 } 67 int mid = (l + r) >> 1; 68 if(L <= mid) { 69 add(ls[x], ls[y], L, R, l, mid); 70 } 71 if(mid < R) { 72 add(rs[x], rs[y], L, R, mid + 1, r); 73 } 74 return; 75 } 76 77 LL ask(int x, int y, int L, int R, int l, int r, int vx, int vy) { 78 if(L <= l && r <= R) { 79 return sum[y] - sum[x] + 1ll * (vy - vx) * (r - l + 1); 80 } 81 vx += tag[x]; 82 vy += tag[y]; 83 int mid = (l + r) >> 1; 84 LL ans = 0; 85 if(L <= mid) { 86 ans += ask(ls[x], ls[y], L, R, l, mid, vx, vy); 87 } 88 if(mid < R) { 89 ans += ask(rs[x], rs[y], L, R, mid + 1, r, vx, vy); 90 } 91 return ans; 92 } 93 94 inline void add(int x, int time) { 95 while(x) { 96 add(rt[time - 1], rt[time], pos[top[x]], pos[x], 1, n); 97 x = fa[top[x]]; 98 } 99 return; 100 } 101 102 inline LL ask(int x, int y, int z) { 103 LL ans = 0; 104 while(z) { 105 ans += ask(rt[x - 1], rt[y], pos[top[z]], pos[z], 1, n, 0, 0); 106 z = fa[top[z]]; 107 } 108 return ans; 109 } 110 111 int main() { 112 int q; 113 scanf("%d%d", &n, &q); 114 for(int i = 2, x; i <= n; i++) { 115 scanf("%d", &x); 116 adde(x + 1, i); 117 } 118 DFS1(1); 119 DFS2(1, 1); 120 for(int i = 1; i <= n; i++) { 121 add(i, i); 122 } 123 for(int i = 1, x, y, z; i <= q; i++) { 124 scanf("%d%d%d", &x, &y, &z); 125 LL t = ask(x + 1, y + 1, z + 1); 126 printf("%lld\n", t % 201314); 127 } 128 return 0; 129 }