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 118 119 120
| #include <bits/stdc++.h> using namespace std; typedef long long ll;
const int MAXN = 1e5 + 5;
vector<int> G[MAXN]; set<pair<int, int> > S[MAXN];
struct Segment_Tree { #define lson(u) node[u].l #define rson(u) node[u].r #define val(u) node[u].val #define tag(u) node[u].tag struct Node { int l, r; ll val, tag; }node[MAXN << 1]; int R, cnt; void pushup(int u) { val(u) = val(lson(u)) + val(rson(u)); } void pushdown(int u, int l, int r) { if (tag(u) == 0) return; int mid = (l + r) >> 1; int llen = mid - l + 1, rlen = r - mid; val(lson(u)) += 1ll * llen * tag(u), val(rson(u)) += 1ll * rlen * tag(u); tag(lson(u)) += tag(u), tag(rson(u)) += tag(u); tag(u) = 0; } void build(int& u, int l, int r) { u = ++cnt; if (l == r) return; int mid = (l + r) >> 1; build(lson(u), l, mid), build(rson(u), mid + 1, r); pushup(u); } void modify_range(int u, int l, int r, int ql, int qr, ll val) { if (ql <= l && r <= qr) { val(u) += 1ll * (r - l + 1) * val; tag(u) += val; return; } pushdown(u, l, r); int mid = (l + r) >> 1; if (ql <= mid) modify_range(lson(u), l, mid, ql, qr, val); if (mid < qr) modify_range(rson(u), mid + 1, r, ql, qr, val); pushup(u); } ll query_range(int u, int l, int r, int ql, int qr) { if (ql <= l && r <= qr) return val(u); pushdown(u, l, r); int mid = (l + r) >> 1; ll ret = 0; if (ql <= mid) ret += query_range(lson(u), l, mid, ql, qr); if (mid < qr) ret += query_range(rson(u), mid + 1, r, ql, qr); return ret; } }T;
int n, q; int dfn[MAXN], size[MAXN], dfn_idx;
void dfs(int u, int fa) { dfn[u] = ++dfn_idx; size[u] = 1; for (auto v : G[u]) { if (v == fa) continue; dfs(v, u); size[u] += size[v]; } }
int main() { scanf("%d%d", &n, &q); for (int i = 1; i < n; ++i) { int u, v; scanf("%d%d", &u, &v); G[u].push_back(v), G[v].push_back(u); } dfs(1, 0); T.build(T.R, 1, n); while (q--) { int op, x, c; scanf("%d%d", &op, &x); int l = dfn[x], r = dfn[x] + size[x] - 1; if (op == 2) { printf("%lld\n", T.query_range(T.R, 1, n, l, r)); } else { scanf("%d", &c); set<pair<int, int> >::iterator it = S[c].lower_bound(make_pair(l, r)); int nl = l, nr = r; if (it != S[c].begin()) { it--; if (it->second >= l) { nl = it->first; nr = max(r, it->second); T.modify_range(T.R, 1, n, it->first, it->second, -1); S[c].erase(it++); } else it++; } while (it != S[c].end() && it->first <= r + 1) { nr = max(r, it->second); T.modify_range(T.R, 1, n, it->first, it->second, -1); S[c].erase(it++); } T.modify_range(T.R, 1, n, nl, nr, 1); S[c].insert(make_pair(nl, nr));
} } return 0; }
|