제출 #1333767

#제출 시각아이디문제언어결과실행 시간메모리
1333767gelastropodWind Turbines (EGOI25_windturbines)C++20
54 / 100
4094 ms61816 KiB
#pragma GCC optimize("O3,inline")
#include <bits/stdc++.h>
using namespace std;
#define int long long

int cnt = 0, cnt1 = 0, ans1 = 0, sqrtN;
vector<vector<int>> adjlist, p2;
vector<int> p, idx, redness, pre, post;

int fin(int n) {
    if (p[n] == n) return n;
    return p[n] = fin(p[n]);
}

void join(int a, int b, int x) {
    a = fin(a);
    b = fin(b);
    if (a == b) return;
    p[b] = a;
    adjlist[cnt].push_back(idx[a]);
    adjlist[cnt].push_back(idx[b]);
    idx[a] = p2[0][idx[a]] = p2[0][idx[b]] = cnt++;
    redness[idx[a]] = x;
    ans1 += x;
}

void dfs(int n) {
    pre[n] = cnt1++;
    for (int i : adjlist[n]) {
        dfs(i);
    }
    post[n] = cnt1 - 1;
}

bool comp(pair<pair<int, int>, int> a, pair<pair<int, int>, int> b) {
    if (a.first.first / sqrtN == b.first.first / sqrtN) return a.first.second < b.first.second;
    return a.first.first / sqrtN < b.first.first / sqrtN;
}

signed main() {
    ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
    int N, M, Q, a, b, c; cin >> N >> M >> Q;
    sqrtN = pow(N, 0.5);
    adjlist.resize(2 * N + 5, vector<int>());
    p2.resize(18, vector<int>(2 * N + 5, -1));
    redness.resize(2 * N + 5, 0);
    pre.resize(2 * N + 5, 0);
    post.resize(2 * N + 5, 0);
    for (int i = 0; i < N; i++) {
        p.push_back(i);
        idx.push_back(i);
    }
    cnt = N;
    vector<pair<int, pair<int, int>>> edges;
    for (int i = 0; i < M; i++) {
        cin >> a >> b >> c;
        edges.push_back({ c, {a, b} });
    }
    sort(edges.begin(), edges.end());
    for (int i = 0; i < M; i++) join(edges[i].second.first, edges[i].second.second, edges[i].first);
    dfs(cnt - 1);
    for (int i = 1; i < 18; i++) {
        for (int j = 0; j < cnt; j++) {
            if (p2[i - 1][j] == -1) p2[i][j] = -1;
            else p2[i][j] = p2[i - 1][p2[i - 1][j]];
        }
    }
    vector<pair<pair<int, int>, int>> quers;
    vector<int> anss(Q, 0);
    for (int i = 0; i < Q; i++) {
        cin >> a >> b;
        quers.push_back({ {a, b}, i });
    }
    sort(quers.begin(), quers.end(), comp);
    pair<int, int> crntr = { 0, 0 };
    set<int> ss;
    int crntv = 0;
    for (int i = 0; i < Q; i++) {
        while (crntr.second <= quers[i].first.second) {
            if (ss.empty()) {
                ss.insert(pre[crntr.second]);
                crntr.second++;
                continue;
            }
            int aa = crntr.second;
            for (int j = 17; j >= 0; j--) if (p2[j][aa] != -1 && ss.upper_bound(post[p2[j][aa]]) == ss.lower_bound(pre[p2[j][aa]])) aa = p2[j][aa];
            aa = p2[0][aa];
            crntv += redness[aa];
            ss.insert(pre[crntr.second]);
            crntr.second++;
        }
        while (crntr.first > quers[i].first.first) {
            crntr.first--;
            if (ss.empty()) {
                ss.insert(pre[crntr.first]);
                continue;
            }
            int aa = crntr.first;
            for (int j = 17; j >= 0; j--) if (p2[j][aa] != -1 && ss.upper_bound(post[p2[j][aa]]) == ss.lower_bound(pre[p2[j][aa]])) aa = p2[j][aa];
            aa = p2[0][aa];
            crntv += redness[aa];
            ss.insert(pre[crntr.first]);
        }
        while (crntr.second > quers[i].first.second + 1) {
            crntr.second--;
            ss.erase(pre[crntr.second]);
            if (ss.empty()) continue;
            int aa = crntr.second;
            for (int j = 17; j >= 0; j--) if (p2[j][aa] != -1 && ss.upper_bound(post[p2[j][aa]]) == ss.lower_bound(pre[p2[j][aa]])) aa = p2[j][aa];
            aa = p2[0][aa];
            crntv -= redness[aa];
        }
        while (crntr.first < quers[i].first.first) {
            ss.erase(pre[crntr.first]);
            if (ss.empty()) {
                crntr.first++;
                continue;
            }
            int aa = crntr.first;
            for (int j = 17; j >= 0; j--) if (p2[j][aa] != -1 && ss.upper_bound(post[p2[j][aa]]) == ss.lower_bound(pre[p2[j][aa]])) aa = p2[j][aa];
            aa = p2[0][aa];
            crntv -= redness[aa];
            crntr.first++;
        }
        anss[quers[i].second] = crntv;
    }
    for (int i : anss) cout << ans1 - i << '\n';
}
#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...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...