树剖70TLE求调 求大佬救救孩子吧 悬赏一个关注
查看原帖
树剖70TLE求调 求大佬救救孩子吧 悬赏一个关注
384381
agosto楼主2023/7/26 17:10
#include<iostream>
#include<vector>
using namespace std;
#define mid ((l+r)/2)
#define ls rt*2,l,mid
#define rs rt*2+1,mid+1,r
const int maxn = 1e6 + 5;
vector<int>g[maxn];
int n, m;
struct node {
    int l, r, s;
};
node tree[maxn];
node merge(node a, node b) {
    node c;
    c.s = a.s + b.s;
    if (b.l == a.r) {
        c.s--;
    }
    c.l = a.l;
    c.r = b.r;
    return c;
}
int tot, tag[maxn], w[maxn], idx[maxn], fa[maxn], depth[maxn], len[maxn], son[maxn], topf[maxn];
bool ftag[maxn], used[maxn];
void pushdown(int rt, int l, int r) {
    if (ftag[rt] == 0) {
        return;
    }
    tree[rt].l = tag[rt];
    tree[rt].r = tag[rt];
    tree[rt].s = 1;
    tag[rt * 2] = tag[rt];
    tag[rt * 2 + 1] = tag[rt];
    tag[rt] = 0;
    ftag[rt * 2] = 1;
    ftag[rt * 2 + 1] = 1;
    ftag[rt] = 0;
}
void pushup(int rt, int l, int r) {
    pushdown(rt, l, r);
    pushdown(ls);
    pushdown(rs);
    tree[rt] = merge(tree[rt * 2], tree[rt * 2 + 1]);
}
void update(int rt, int l, int r, int L, int R, int v) {
    pushdown(rt, l, r);
    if (L <= l && r <= R) {
        ftag[rt] = 1;
        tag[rt] = v;
        return;
    }
    if (L <= mid) {
        update(ls, L, R, v);
    }
    if (R > mid) {
        update(rs, L, R, v);
    }
    pushup(rt, l, r);
}
node query(int rt, int l, int r, int L, int R) {
    pushdown(rt, l, r);
    if (L <= l && r <= R) {
        return tree[rt];
    } else if (L > mid) {
        return query(rs, L, R);
    } else if (R <= mid) {
        return query(ls, L, R);
    } else {
        return merge(query(ls, L, R), query(rs, L, R));
    }
}
void updaterange(int x, int y, int z) {
    while (topf[x] != topf[y]) {
        int fx = topf[x], fy = topf[y];
        if (depth[fx] < depth[fy]) {
            swap(fx, fy);
            swap(x, y);
        }
        update(1, 1, n, idx[fx], idx[x], z);
        x = fa[fx];
    }
    if (depth[x] < depth[y]) {
        swap(x, y);
    }
    update(1, 1, n, idx[y], idx[x], z);
}
int queryrange(int x, int y) {
    int ans = 0, las, lst;
    las = lst = -1;
    while (topf[x] != topf[y]) {
        int fx = topf[x], fy = topf[y];
        if (depth[fx] < depth[fy]) {
            swap(fx, fy);
            swap(x, y);
            swap(las, lst);
        }
        node t = query(1, 1, n, idx[fx], idx[x]);
        ans += t.s;
        if (t.r == las) {
            ans--;
        }
        las = t.l;
        x = fa[fx];
    }
    if (depth[x] < depth[y]) {
        swap(x, y);
        swap(las, lst);
    }
    node t = query(1, 1, n, idx[y], idx[x]);
    ans += t.s;
    if (t.r == las) {
        ans--;
    }
    if (t.l == lst) {
        ans--;
    }
    return ans;
}
void dfs1(int u, int f, int deep) {
    depth[u] = deep;
    fa[u] = f;
    len[u] = 1;
    for (int i = 0; i < g[u].size(); i++) {
        int v = g[u][i];
        if (f == v) {
            continue;
        }
        dfs1(v, u, deep + 1);
        len[u] += len[v];
        if (len[son[u] < len[v]]) {
            son[u] = v;
        }
    }
}
void dfs2(int u, int f) {
    if (u == 0) {
        return;
    }
    topf[u] = f;
    used[u] = 1;
    idx[u] = ++tot;
    dfs2(son[u], f);
    for (int i = 0; i < g[u].size(); i++) {
        int v = g[u][i];
        if (used[v] != 0) {
            continue;
        }
        dfs2(v, v);
    }

}
int main() {
    ios::sync_with_stdio(false);
    cin >> n >> m;
    for (int i = 1; i <= n; i++) {
        cin >> w[i];
    }
    for (int i = 1; i <= n - 1; i++) {
        int u, v;
        cin >> u >> v;
        g[u].push_back(v);
        g[v].push_back(u);
    }
    dfs1(1, 0, 1);
    dfs2(1, 1);
    for (int i = 1; i <= n; i++) {
        update(1, 1, n, idx[i], idx[i], w[i]);
    }
    for (int i = 1; i <= m; i++) {
        char x;
        int a, b, c;
        cin >> x;
        if (x == 'C') {
            cin >> a >> b >> c;
            updaterange(a, b, c);
        } else {
            cin >> a >> b;
            cout << queryrange(a, b) << endl;
        }
    }
    return 0;
}
2023/7/26 17:10
加载中...