树剖样例没有输出求调,悬一关

P3384 【模板】重链剖分/树链剖分

zhangxiao666 @ 2024-01-18 22:32:13

rt,只A了#11,样例没有输出qwq,过路大佬求求帮忙调一调,悬赏一关。

#include <bits/stdc++.h>
#define int long long
using namespace std;
const int N = 1e5 + 10;
int n, q, r, mod, cnt;
int a[N], now[N];
int head[N], to[2 * N], nxt[2 * N];
int fa[N], son[N], siz[N], dep[N], top[N], id[N];
int tr[N], add[N];

void add_edge(int x, int y)
{
    cnt++;
    to[cnt] = y;
    nxt[cnt] = head[x];
    head[x] = cnt;
}

void dfs1(int x, int father)
{
    siz[x] = 1;
    fa[x] = father;
    dep[x] = dep[father] + 1;
    for(int i = head[x]; i; i = nxt[i])
    {
        if(to[i] == father) continue;
        dfs1(to[i], x);
        siz[x] += siz[to[i]];
        if(siz[son[x]] < siz[to[i]]) son[i] = to[i];
    }
}

void dfs2(int x, int tp)
{
    id[x] = ++cnt;
    now[cnt] = a[x];
    top[x] = tp;
    if(!son[x]) return;
    dfs2(son[x], tp);
    for(int i = head[x]; i; i = nxt[i])
    {
        if(id[to[i]]) continue;
        dfs2(to[i], to[i]);
    }
}

void pushup(int x)
{
    tr[x] = tr[x << 1] + tr[x << 1 | 1];
    tr[x] %= mod;
}

void build(int x, int l, int r)
{
    if(l == r) {tr[x] = now[l]; return;}
    int mid = l + r >> 1;
    build(x << 1, l, mid), build(x << 1 | 1, mid + 1, r);
    pushup(x);
}

void change(int x, int l, int r, int sum)
{
    tr[x] += (r - l + 1) * sum % mod;
    add[x] += sum;
    add[x] %= mod;
}

void pushdown(int x, int l, int r)
{
    int mid = l + r >> 1;
    change(x << 1, l, mid, add[x]);
    change(x << 1 | 1, mid + 1, r, add[x]);
    add[x] = 0;
}

void update(int x, int l, int r, int ql, int qr, int k)
{
    if(ql <= l && r <= qr) {change(x, l, r, k); return;}
    int mid = l + r >> 1;
    pushdown(x, l, r);
    if(ql <= mid) update(x << 1, l, mid, ql, qr, k);
    if(qr > mid) update(x << 1 | 1, mid + 1, r, ql, qr, k);
    pushup(x);
}

int query(int x, int l, int r, int ql, int qr)
{
    if(ql <= l && r <= qr) return tr[x];
    int mid = l + r >> 1, ans = 0;
    pushdown(x, l, r);
    if(ql <= mid) ans += query(x << 1, l, mid, ql, qr);
    if(qr > mid) ans += query(x << 1 | 1, mid + 1, r, ql, qr);
    ans %= mod;
    return ans;
}

void update_tree(int x, int y, int k)
{
    k %= mod;
    while(top[x] != top[y])
    {
        if(dep[top[x]] < dep[top[y]]) swap(x, y);
        update(1, 1, n, id[top[x]], id[x], k);
        x = fa[top[x]];
    }
    if(dep[x] > dep[y]) swap(x, y);
    update(1, 1, n, id[x], id[y], k);
}

int query_tree(int x, int y)
{
    int ans = 0;
    while(top[x] != top[y])
    {
        if(dep[top[x]] < dep[top[y]]) swap(x, y);
        ans += query(1, 1, n, id[top[x]], id[x]);
        ans %= mod;
        x = fa[top[x]];
    }
    if(dep[x] > dep[y]) swap(x, y);
    ans += query(1, 1, n, id[x], id[y]);
    return ans % mod;
}

void update_son(int x, int k)
{
    k %= mod;
    update(1, 1, n, id[x], id[x] + siz[x] - 1, k);
}

int query_son(int x)
{
    int ans = query(1, 1, n, id[x], id[x] + siz[x] - 1);
    return ans % mod;
}

signed main()
{
    std::ios::sync_with_stdio(false);
    cin.tie(0), cout.tie(0);
    cin >> n >> q >> r >> mod;
    for(int i = 1; i <= n; i++) 
    {
        cin >> a[i];
        a[i] %= mod;
    }
    for(int i = 1; i < n; i++)
    {
        int x, y;
        cin >> x >> y;
        add_edge(x, y);
        add_edge(y, x);
    }
    cnt = 0;
    dfs1(r, 0);
    dfs2(r, r);
    build(1, 1, n);
    while(q--)
    {
        int op;
        cin >> op;
        if(op == 1)
        {
            int x, y, z;
            cin >> x >> y >> z;
            update_tree(x, y, z);
        }
        if(op == 2)
        {
            int x, y;
            cin >> x >> y;
            cout << query_tree(x, y) << "\n";
        }
        if(op == 3)
        {
            int x, y;
            cin >> x >> y;
            update_son(x, y);
        }
        if(op == 4)
        {
            int x;
            cin >> x;
            cout << query_son(x) << "\n";
        }
    }
    return 0;
}

by sansesantongshun @ 2024-01-19 13:21:20

on line 29,

        if(siz[son[x]] < siz[to[i]]) son[i] = to[i];

改为

        if(siz[son[x]] < siz[to[i]]) son[x] = to[i];

by zhangxiao666 @ 2024-01-20 11:20:26

@sansesantongshun thanks,wssb


|