제출 #1346167

#제출 시각아이디문제언어결과실행 시간메모리
1346167nguyenkhangninh99Grapevine (NOI22_grapevine)C++20
35 / 100
79 ms20124 KiB
#include<bits/stdc++.h>
using namespace std;

#define int long long
const int maxn = 1e5 + 5;
int tin[maxn], out[maxn], val[maxn], par[maxn], mnd[maxn], at[maxn], up[maxn], timedfs;
vector<pair<int, int>> g[maxn];
int st[4 * maxn], lazy[4 * maxn];

void apply(int id, int x){
    st[id] += x;
    lazy[id] += x;
}

void down(int id){
    apply(id * 2, lazy[id]);
    apply(id * 2 + 1, lazy[id]);
    lazy[id] = 0;
}

void update(int id, int l, int r, int p, int x){
    if(l == r) st[id] += x;
    else{
        down(id);
        int mid = (l + r) / 2;
        if(p <= mid) update(id * 2, l, mid, p, x);
        else update(id * 2 + 1, mid + 1, r, p, x);
        st[id] = min(st[id * 2], st[id * 2 + 1]);
    }
}

void assign(int id, int l, int r, int u, int v, int x){
    if(v < l || r < u) return;
    if(u <= l && r <= v) apply(id, x);
    else{
        down(id);
        int mid = (l + r) / 2;
        assign(id * 2, l, mid, u, v, x);
        assign(id * 2 + 1, mid + 1, r, u, v, x);
        st[id] = min(st[id * 2], st[id * 2 + 1]);
    }
}

void dfs(int u, int p){
    tin[u] = ++timedfs;
    par[u] = p;
    for(auto [v, w]: g[u]){
        if(v == p) continue;
        val[v] = val[u] + w;
        up[v] = w;
        dfs(v, u);
    }
    out[u] = timedfs;
    val[u] += 1e15;
}

void diddy(int u){
    mnd[u] = (at[u] ? 0 : 1e15);
    for(auto [v, w]: g[u]) if(tin[v] > tin[u]) mnd[u] = min(mnd[u], up[v] + mnd[v]); 
}

signed main(){
    ios_base::sync_with_stdio(false);
    cin.tie(0); cout.tie(0);

    int n, q; cin >> n >> q;

    bool subtask3 = 1;

    for(int i = 1; i <= n - 1; i++){
        int u, v, w; cin >> u >> v >> w;
        subtask3 &= (u == (i + 1) / 2 && v == i + 1);
        g[u].push_back({v, w});
        g[v].push_back({u, w});
    }   
    for(int i = 1; i <= n; i++) mnd[i] = 1e15;
    dfs(1, 0);
    if(subtask3 || max(n, q) <= 2000){
        while(q--){
            int type; cin >> type;

            if(type == 1){ 
                int x; cin >> x;
                int ans = 1e15, curd = 0, cur = x;
                while(cur >= 1){
                    ans = min(ans, curd + mnd[cur]);
                    curd += up[cur];
                    cur = par[cur];
                }

                cout << (ans >= 1e15 ? -1: ans) << "\n";
            }else if(type == 2){ 
                int u; cin >> u;
                at[u] = !at[u]; 
                int cur = u;
                while(cur >= 1){
                    diddy(cur);
                    cur = par[cur];
                }
            }else{ 
                int u, v, w; cin >> u >> v >> w;
                if(tin[v] > tin[u]) swap(u, v);
                up[u] = w;
                int cur = u;
                while(cur >= 1){
                    diddy(cur);
                    cur = par[cur];
                }
            }
        }
        return 0;
    }
    for(int i = 1; i <= n; i++) update(1, 1, n, tin[i], val[i]);
    while(q--){
        int type; cin >> type;
        if(type == 1){
            int q_idx; cin >> q_idx;
            cout << (st[1] >= 1e15 ? -1 : st[1]) << "\n";
        }
        if(type == 2){
            int x; cin >> x;
            update(1, 1, n, tin[x], (at[x] ? 1e15 : -1e15));
            at[x] = !at[x];
        }
        if(type == 3){
            int a, b, x; cin >> a >> b >> x;
            if(tin[a] > tin[b]) swap(a, b);
            assign(1, 1, n, tin[b], out[b], x - up[b]);
            up[b] = x;
        }
    }
    return 0;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...