线段树求调
  • 板块灌水区
  • 楼主danzong_dan
  • 当前回复5
  • 已保存回复5
  • 发布时间2024/8/14 13:14
  • 上次更新2024/8/14 15:04:52
查看原帖
线段树求调
715456
danzong_dan楼主2024/8/14 13:14

wa10

#include <cstdio>
#include <cmath>
#include <algorithm>

const int maxn = 1145144;

int a[maxn];
long long tag[4 * maxn];
long long tr[4 * maxn];

auto bf = [](auto x, auto y) { return x + y; };
void apply(int u, int l, int r) {
	tag[u] = sqrt(tr[u]);
	tr[u] = sqrt(tr[u]);
}

void apply2(int u, int l, int r, int x) {
	tr[u] += (long long)(r - l + 1) * (x);
	tag[u] += x;
}

void build(int u, int l, int r) {
	if (l == r) {
		tr[u] = a[l];
		return;
	}
	int mid = (l + r) / 2;
	build(u * 2, l, mid);
	build(u * 2 + 1, mid + 1, r);
	tr[u] = tr[u * 2] + tr[u * 2 + 1];
}

void pushdown(int u, int l, int r) {
    if (tag[u]) {
        int mid = (l + r) / 2;
        apply2(u * 2, l, mid, tag[u]);
        apply2(u * 2 + 1, mid + 1, r, tag[u]);
        tag[u] = 0;
    }
}

void update(int u, int l, int r, int s, int t) {
    if (s <= l && r <= t) {
        apply(u, l, r);
        return ;
    }
    pushdown(u, l, r);
    int mid = (l + r) / 2;
    if (s <= mid) update(u * 2, l, mid, s, t);
    if (t > mid) update(u * 2 + 1, mid + 1, r, s, t);
    tr[u] = bf(tr[u * 2], tr[u * 2 + 1]);
}

long long query(int u, int l, int r, int s, int t) {
    if (s <= l && r <= t) return tr[u];
    pushdown(u, l, r);
    int mid = (l + r) / 2;
    if (t <= mid) return query(u * 2, l, mid, s, t);
    if (s > mid) return query(u * 2 + 1, mid + 1, r, s, t);
    return bf(query(u * 2, l, mid, s, t), query(u * 2 + 1, mid + 1, r, s, t));
}

int n, q;

int main() {
	std::scanf("%d", &n);
	for (int i = 1; i <= n; ++i) std::scanf("%d", a + i);
	build(1, 1, n);
	
	std::scanf("%d", &q);

	while (q--) {
		int op, x, y;
		std::scanf("%d %d %d", &op, &x, &y);
		if (op == 1) {
			std::printf("%lld\n", query(1, 1, n, x, y));
		} else {
			update(1, 1, n, x, y);
		}
	}

	return 0;
}
2024/8/14 13:14
加载中...