社区讨论

线段树暴力区修求调

P4145上帝造题的七分钟 2 / 花神游历各国参与者 2已保存回复 3

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
3 条
当前快照
1 份
快照标识符
@mhjifzr1
此快照首次捕获于
2025/11/04 03:05
4 个月前
此快照最后确认于
2025/11/04 03:05
4 个月前
查看原帖
应该可以线段树上暴力吧,每个节点应该最多开6次? 但是tletle 求助
CPP
#include <bits/stdc++.h>
#define int long long

template <class Info>

struct SGT {
#define lc rt << 1
#define rc rt << 1 | 1

    struct node {
        int l, r;
        Info info;
    };

    std::vector<node> tree;
    int n;

    SGT(const std::vector<Info> &num, const int &_n) : n(_n), tree(4 * _n + 5) {
        auto build = [&](auto &&self, int rt, int l, int r) -> void {
            tree[rt] = {l, r, num[l]};

            if (l == r) {
                return;
            }

            int m = l + r >> 1;

            self(self, lc, l, m);
            self(self, rc, m + 1, r);

            tree[rt].info = tree[lc].info + tree[rc].info;
        };

        build(build, 1, 1, n);
    }

    void update(int rt, int l, int r) {
        if (tree[rt].info.mx == 1) {
            return;
        }
        if (tree[rt].l == tree[rt].r) {
            keep(rt);
            return;
        }

        int m = tree[rt].l + tree[rt].r >> 1;

        if (l <= m) {
            update(lc, l, r);
        }
        if (r > m) {
            update(rc, l, r);
        }

        tree[rt].info = tree[lc].info + tree[rc].info;
    }

    Info query(int rt, int l, int r) {
        if (l <= tree[rt].l && tree[rt].r <= r) {
            return tree[rt].info;
        }

        int m = tree[rt].l + tree[rt].r >> 1;
        Info sum;

        if (l <= m) {
            sum = sum + query(lc, l, r);
        }
        if (r > m) {
            sum = sum + query(rc, l, r);
        }

        return sum;
    }

    void keep(int rt) {
        tree[rt].info.num = sqrt(tree[rt].info.num);
        tree[rt].info.mx = sqrt(tree[rt].info.mx);
    }
};

struct Info {
    int num, mx;
    Info() {
        num = mx = 0;
    }
    Info(int _num) {
        num = mx = _num;
    }
};

Info operator+(const Info &a, const Info &b) {
    Info c;
    c.num = a.num + b.num;
    c.mx = std::max(a.mx, b.mx);
    return c;
}

void solve() {
    int n;
    std::cin >> n;

    std::vector<Info> v(n + 1);
    for (int i = 1; i <= n; i++) {
        std::cin >> v[i].num;
    }

    SGT<Info> sgt(v, n);

    int m;
    std::cin >> m;

    for (int i = 1; i <= m; i++) {
        int ops, l, r;
        std::cin >> ops >> l >> r;
        
        if(l > r) {
            std::swap(l,r);
        }


        if (ops == 0) {
            sgt.update(1, l, r);
        }
        if (ops == 1) {
            std::cout << sgt.query(1, l, r).num << '\n';
        }
    }
}

signed main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(0), std::cout.tie(0);

    int t = 1;

    while (t--) {
        solve();
    }

    return 0;
}

回复

3 条回复,欢迎继续交流。

正在加载回复...