60颗线段树没有前途(T﹏T)
查看原帖
60颗线段树没有前途(T﹏T)
249422
TinyMirror1楼主2021/10/31 20:54

TLE了,能优化吗

#include <iostream>
#include <cstdio>
#include <bitset>
using namespace std;
const int maxn = 4e5 + 5;
inline int read() {
	int x = 0; char ch = getchar();
	while (ch < '0' || ch > '9') {
		ch = getchar();
	}
	while (ch >= '0' && ch <= '9') {
		x = x * 10 + (ch ^ 48);
		ch = getchar();
	}
	return x;
}
struct Edge {
	int to, next;
} ed[maxn << 1];
int first[maxn], en = 2;
inline void insert(int x, int y) {
	ed[en].to = y;
	ed[en].next = first[x];
	first[x] = en++;
}
int in[maxn], out[maxn], tot;
void dfs(int now, int fa) {
	in[now] = ++tot;
	for (int i = first[now]; i; i = ed[i].next) {
		int x = ed[i].to;
		if (x == fa) continue;
		dfs(x, now);
	}
	out[now] = tot;
}
short int a[maxn];
bitset<maxn << 2> T[61], cov0[61], cov1[61];
inline void pushup(int id, int k) {
	T[k][id] = T[k][id << 1] | T[k][id << 1 | 1];
}
inline void pushdown(int id, int k) {
	int l = id << 1, r = id << 1 | 1;
	if (cov0[k][id]) {
		T[k][l] = T[k][r] = false;
		cov0[k][l] = cov0[k][r] = true;
		cov1[k][l] = cov1[k][r] = false;
		cov0[k][id] = false;
	}
	if (cov1[k][id]) {
		T[k][l] = T[k][r] = true;
		cov1[k][l] = cov1[k][r] = true;
		cov0[k][l] = cov0[k][r] = false;
		cov1[k][id] = false;
	}
}
void update(int id, int l, int r, int x, int y, bool op, int k) {
	if (x <= l && r <= y) {
		T[k][id] = op;
		if (op) {
			cov1[k][id] = true;
			cov0[k][id] = false;
		} else {
			cov0[k][id] = true;
			cov1[k][id] = false;
		}
		return;
	}
	pushdown(id, k);
	int mid = (l + r) >> 1;
	if (x <= mid) update(id << 1, l, mid, x, y, op, k);
	if (y > mid) update(id << 1 | 1, mid + 1, r, x, y, op, k);
	pushup(id, k);
}
bool flag = false;
void query(int id, int l, int r, int x, int y, int k) {
	if (flag) return;
	if (x <= l && r <= y) {
		flag = flag | T[k][id];
		return;
	}
	pushdown(id, k);
	int mid = (l + r) >> 1;
	if (x <= mid) query(id << 1, l, mid, x, y, k);
	if (y > mid) query(id << 1 | 1, mid + 1, r, x, y, k);
}
int n, m;
int count(int l, int r) {
	int cnt = 0;
	for (int j = 1; j <= 60; j++) {
		flag = false;
		query(1, 1, n, l, r, j);
		cnt += flag;
	}
	return cnt;
}
int main() {
	n = read(), m = read();
	for (int i = 1; i <= n; i++) a[i] = read();
	for (int i = 1; i < n; i++) {
		int x = read(), y = read();
		insert(x, y); insert(y, x);
	}
	dfs(1, -1);
	for (int i = 1; i <= n; i++) {
		update(1, 1, n, in[i], in[i], true, a[i]);
	}
	while (m--) {
		int op = read();
		if (op == 1) {
			int x = read(), c = read();
			for (int j = 1; j <= 60; j++) {
				update(1, 1, n, in[x], out[x], false, j);
			}
			update(1, 1, n, in[x], out[x], true, c);
		}
		if (op == 2) {
			int x = read();
			printf("%d\n", count(in[x], out[x]));
		}
	}
	return 0;
}
2021/10/31 20:54
加载中...