题解 CF375D Tree and Queries
Posted little-sun0331
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了题解 CF375D Tree and Queries相关的知识,希望对你有一定的参考价值。
首先,子树上的查询问题可以通过$DFS$序转为序列问题
再一看,没有修改,可以离线,这不就是莫队吗?
我们用$sum_i$表示出现次数$geq i$的个数
用$val_i$表示第$i$种颜色的出现次数
那么每次修改时只要$O(1)$修改$sum$和$val$即可
详见代码
1 #include <bits/stdc++.h> 2 const int MaxN = 100010; 3 struct node 4 { 5 int val, dfn, r, id; 6 }; 7 struct query 8 { 9 int l, r; 10 int pos, id, k; 11 }; 12 struct edge 13 { 14 int next, to; 15 }; 16 node a[MaxN]; 17 query q[MaxN]; 18 edge e[MaxN << 1]; 19 int n, m, cnt, dfscnt, size; 20 int head[MaxN], ans[MaxN], sum[MaxN], val[MaxN]; 21 inline int comp(node a, node b) { return a.dfn < b.dfn; } 22 inline int cmp(query a, query b) 23 { 24 if (a.pos != b.pos) 25 return a.pos < b.pos; 26 return a.r < b.r; 27 } 28 inline void add_edge(int u, int v) 29 { 30 ++cnt; 31 e[cnt].to = v; 32 e[cnt].next = head[u]; 33 head[u] = cnt; 34 } 35 inline void dfs(int u) 36 { 37 a[u].dfn = ++dfscnt; 38 for (int i = head[u]; i; i = e[i].next) 39 { 40 int v = e[i].to; 41 if (!a[v].dfn) 42 dfs(v); 43 } 44 a[u].r = dfscnt; 45 } 46 inline int read() 47 { 48 int x = 0; 49 char ch = getchar(); 50 while (ch > ‘9‘ || ch < ‘0‘) 51 ch = getchar(); 52 while (ch <= ‘9‘ && ch >= ‘0‘) 53 x = (x << 1) + (x << 3) + (ch ^ 48), ch = getchar(); 54 return x; 55 } 56 inline void add(int x) { ++val[a[x].val], ++sum[val[a[x].val]]; } 57 inline void del(int x) { --sum[val[a[x].val]], --val[a[x].val]; } 58 inline void solve() 59 { 60 int l = 1, r = 0; 61 for (int i = 1; i <= m; i++) 62 { 63 while (l > q[i].l) 64 --l, add(l); 65 while (r < q[i].r) 66 ++r, add(r); 67 while (l < q[i].l) 68 del(l), ++l; 69 while (r > q[i].r) 70 del(r), --r; 71 ans[q[i].id] = sum[q[i].k]; 72 } 73 } 74 int main() 75 { 76 n = read(), m = read(); 77 size = pow(n, 0.55); 78 for (int i = 1; i <= n; i++) 79 a[i].val = read(), a[i].id = i; 80 for (int i = 1; i <= n - 1; i++) 81 { 82 int u = read(), v = read(); 83 add_edge(u, v); 84 add_edge(v, u); 85 } 86 dfs(1); 87 for (int i = 1; i <= m; i++) 88 { 89 int v, k; 90 v = read(), k = read(); 91 q[i].l = a[v].dfn, q[i].r = a[v].r, q[i].k = k; 92 q[i].id = i, q[i].pos = (q[i].l - 1) / size + 1; 93 } 94 std::sort(q, q + m + 1, cmp); 95 std::sort(a + 1, a + n + 1, comp); 96 solve(); 97 for (int i = 1; i <= m; i++) 98 printf("%d ", ans[i]); 99 return 0; 100 }
以上是关于题解 CF375D Tree and Queries的主要内容,如果未能解决你的问题,请参考以下文章
CodeForces 375D Tree and Queries 莫队||DFS序
Codeforces 375D D. Tree and Queries
[Codeforces375D]Tree and Queries(莫队算法)