제출 #573129

#제출 시각아이디문제언어결과실행 시간메모리
573129tengiz05Joker (BOI20_joker)C++17
0 / 100
2074 ms8036 KiB
#include <bits/stdc++.h>

using i64 = long long;

int main() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(nullptr);
    
    int n, m, q;
    std::cin >> n >> m >> q;
    
    std::vector<int> from(m), to(m);
    for (int i = 0; i < m; i++) {
        std::cin >> from[i] >> to[i];
        from[i]--;
        to[i]--;
    }
    
    std::vector<int> p(n), c(n), rank(n);
    std::iota(p.begin(), p.end(), 0);
    
    auto leader = [&](int u) {
        while (u != p[u]) u = p[u];
        return u;
    };
    
    auto color = [&](int u) {
        int x = c[u];
        while (u != p[u]) {
            u = p[u];
            x ^= c[u];
        }
        return x;
    };
    
    int cnt = 0;
    
    std::vector<std::tuple<int, int, int, int>> h;
    
    auto merge = [&](int id) {
        int u = from[id];
        int v = to[id];
        int a = leader(u);
        int b = leader(v);
        h.emplace_back(id, a, b, color(u) == color(v));
        if (a == b) {
            if (color(u) == color(v)) {
                cnt++;
            }
        } else {
            if (color(u) == color(v)) {
                c[b] ^= c[a];
                c[b] ^= 1;
            }
            if (rank[a] > rank[b]) {
                p[b] = a;
                rank[a]++;
            } else {
                p[a] = b;
                rank[b]++;
            }
        }
        return;
    };
    
    auto unmerge = [&]() {
        auto [id, a, b, col] = h.back();
        h.pop_back();
        if (a == b) {
            if (col) {
                cnt--;
            }
        } else {
            if (col) {
                c[b] ^= c[a];
                c[b] ^= 1;
            }
            if (rank[a] > rank[b]) {
                p[b] = b;
                rank[a]--;
            } else {
                p[a] = a;
                rank[b]--;
            }
        }
    };
    auto rollback = [&](int x) {
        while (x--) {
            assert(!h.empty());
            unmerge();
        }
    };
    
    std::vector<int> opt(m);
    
    std::function<void(int, int, int, int)> dfs = [&](int l, int r, int optl, int optr) {
        if (l > r)
            return;
        int m = (l + r) / 2;
        
        for (int i = l; i < m; i++) {
            merge(i);
        }
        
        opt[m] = optr;
        while (cnt == 0 && opt[m] >= m) {
            merge(opt[m]);
            opt[m]--;
        }
        
        rollback(optr - opt[m]);
        merge(m);
        dfs(m + 1, r, opt[m], optr);
        rollback(m - l + 1);
        
        for (int i = opt[m] + 1; i <= optr; i++) {
            merge(i);
        }
        dfs(l, m - 1, optl, opt[m]);
        rollback(optr - opt[m]);
    };
    
    // dfs(0, m - 1, 0, m - 1);
    
    for (int i = 0; i < m; i++) {
        int j = m - 1;
        while (cnt == 0 && j >= i) {
            merge(j);
            j--;
        }
        opt[i] = j;
        rollback(m - 1 - j);
        merge(i);
    }
    
    // for (int i = 0; i < m; i++) {
        // merge(i);
    // }
    
    while (q--) {
        int l, r;
        std::cin >> l >> r;
        l--;
        r--;
        
        if (cnt && r <= opt[l]) {
            std::cout << "YES\n";
        } else {
            std::cout << "NO\n";
        }
    }
    
    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...