求助,样例2没过

P1253 扶苏的问题

I_like_play_eggy @ 2024-07-15 17:25:39

时隔 24 天再次爆肝此题,写了 5 小时共 180 行 3806 字节,样例 1 过了,样例 2 输出 10,求助

#include <bits/stdc++.h>
#define int long long
#define ls(p) (p<<1)
#define rs(p) (p<<1|1)
using namespace std;

const int maxn = 1e6 + 6;
const int inf = 1ll << 60;
struct SegmentTree // 线段树结构体 
{
    int lazy_add; // 增加 x
    int lazy_upd; // 改为 x
    int max_num;  // 当前区间最大值
}
tree[maxn << 2]; // 开 4 倍空间 
int num[maxn], n, m;
int op, l, r, x;

// 建树 
void build(int pl, int pr, int p)
{
    if (pl == pr) // 子节点 
    {
        tree[p].lazy_upd = -inf;   // 初始化为极小值 
        tree[p].max_num = num[pl]; // 子节点最大值为本身 
        return;
    }
    int mid = (pl + pr) >> 1;
    // 对子区间建树 
    build(pl, mid, ls(p));
    build(mid + 1, pr, rs(p));
    // 更新区间最大值 
    tree[p].max_num = max(
        tree[ls(p)].max_num,
        tree[rs(p)].max_num
    );
}

void addtag(int p, int x, bool isadd) // 打 Lazy_tag
{
    if (isadd) // 如果是增加 x
    {
        tree[p].max_num += x; // 区间最大值增加 x
        if (tree[p].lazy_upd != -inf) // 如果修改过数
        {
            tree[p].lazy_upd += x; // 修改的数增加 x
        }
        else
        {
            tree[p].lazy_add += x; // 增加的数增加 x
        }
    }
    else // 如果是修改 x
    {
        tree[p].max_num  = x; // 区间最大值改为 x
        tree[p].lazy_upd = x; // 修改的数变为 x
        tree[p].lazy_add = 0; // 增加的数变为 0
    }
}

void pushdown(int pl, int pr, int p) // 下传 Lazy_tag
{
    int mid = (pl + pr) >> 1;
    if (tree[p].lazy_upd != -inf) // 如果修改过数 
    {
        // 区间最大值改为 lazy_upd
        tree[ls(p)].max_num  = tree[p].lazy_upd;
        // 修改的数改为 lazy_upd
        tree[ls(p)].lazy_upd = tree[p].lazy_upd;
        // 区间最大值改为 lazy_upd
        tree[rs(p)].max_num  = tree[p].lazy_upd;
        // 修改的数改为 lazy_upd
        tree[rs(p)].lazy_upd = tree[p].lazy_upd;
    }
    else
    {
        // 区间最大值增加 lazy_add
        tree[ls(p)].max_num  += tree[p].lazy_add;
        // 增加的数增加 lazy_add
        tree[ls(p)].lazy_add += tree[p].lazy_add;
        // 区间最大值增加 lazy_add
        tree[rs(p)].max_num  += tree[p].lazy_add;
        // 增加的数增加 lazy_add
        tree[rs(p)].lazy_add += tree[p].lazy_add;
    }
    // 清零该节点 Lazy_tag
    tree[p].lazy_add = 0;
    tree[p].lazy_upd = -inf;
}

// 区间增加 x
void change_add(int pl, int pr, int p, int l, int r, int x)
{
    if (l <= pl && pr <= r) // 完全覆盖此区间
    {
        addtag(p, x, 1); // 打 Lazy_tag
        return;
    }
    pushdown(pl, pr, p); // 下传 lazy_tag
    int mid = (pl + pr) >> 1;
    if (l <= mid) // 包含左区间
    {
        change_add(pl, mid, ls(p), l, r, x);
    }
    if (r > mid) // 包含右区间
    {
        change_add(mid + 1, pr, rs(p), l, r, x);
    }
}

// 区间修改为 x
void change_upd(int pl, int pr, int p, int l, int r, int x)
{
    if (l <= pl && pr <= r) // 完全覆盖此区间
    {
        addtag(p, x, 0); // 打 Lazy_tag
        return;
    }
    pushdown(pl, pr, p); // 下传 lazy_tag
    int mid = (pl + pr) >> 1;
    if (l <= mid) // 包含左区间
    {
        change_upd(pl, mid, ls(p), l, r, x);
    }
    if (r > mid) // 包含右区间
    {
        change_upd(mid + 1, pr, rs(p), l, r, x);
    }
}

// 区间查询最大值 
int query(int pl, int pr, int p, int l, int r)
{
    if (l <= pl && pr <= r) // 完全覆盖此区间
    {
        return tree[p].max_num;
    }
    pushdown(pl, pr, p); // 下传 lazy_tag
    int mid = (pl + pr) >> 1;
    int s = -inf; // 初始化为极小值
    if (l <= mid) // 包含左区间
    {
        s = max(s, query(pl, mid, ls(p), l, r));
    }
    if (r > mid) // 包含右区间
    {
        s = max(s, query(mid + 1, pr, rs(p), l, r));
    }
    return s; // 返回区间最大值
}

signed main()
{
    scanf("%lld %lld", &n, &m);
    for (int i = 1; i <= n; i ++)
    {
        scanf("%lld", &num[i]);
    }
    build(1, n, 1); // 建树 
    for (int i = 1; i <= m; i ++)
    {
        scanf("%lld %lld %lld", &op, &l, &r);
        if (op == 1)
        {
            scanf("%lld", &x);
            change_upd(1, n, 1, l, r, x); // 修改为 x
        }
        if (op == 2)
        {
            scanf("%lld", &x);
            change_add(1, n, 1, l, r, x); // 增加 x
        }
        if (op == 3)
        {
            // 区间查询 
            printf("%lld\n", query(1, n, 1, l, r));
        }
    }
    return 0;
}

by I_like_play_eggy @ 2024-07-15 17:32:49

@SiuuuCR7 @kevinZ99 救命


|