답안 #251228

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
251228 2020-07-20T15:54:23 Z Sorting Pipes (CEOI15_pipes) C++14
80 / 100
4093 ms 65536 KB
#include <bits/stdc++.h>
 
using namespace std;
 
const int k_M = 6e6 + 3;
const int k_N = 1e5 + 3;
const int k_LOG_N = 17;
 
int n, m;
vector<int> adj[k_N];
 
vector<pair<int, int>> edges;
 
int p[k_N], sz[k_N], root[k_N], suffix[k_N];
int up[k_LOG_N][k_N], d[k_N];
 
bool not_critical[k_N];
 
int find_p(int x){
    if(x == p[x]) return x;
    return p[x] = find_p(p[x]);
}
 
int dfs(int x, int parent = -1){
    int sum = 0;
    for(const int &idx: adj[x]){
        int to = (edges[idx].first == x) ? edges[idx].second : edges[idx].first;
        if(to == parent) continue;
 
        int curr = dfs(to, x);
        if(curr) not_critical[idx] = true;
        sum += curr;
    }
 
    return sum += suffix[x];
}
 
void dfs_join(int x, int parent){
    up[0][x] = parent;
    d[x] = d[parent] + 1;
 
    for(int i = 1; i < k_LOG_N; ++i)
        up[i][x] = up[i - 1][up[i - 1][x]];
 
    for(const int &idx: adj[x]){
        int to = (edges[idx].first == x) ? edges[idx].second : edges[idx].first;
        if(to == parent) continue;
        dfs_join(to, x);
    }
}
 
bool unite(int x, int y){
    if(find_p(x) == find_p(y)) return false;
    if(sz[p[x]] < sz[p[y]]) swap(x, y);
 
    dfs(root[p[y]]);
    dfs_join(y, x);
 
    sz[p[x]] += sz[p[y]];
    p[p[y]] = p[x];
    return true;
}
 
int get_lca(int u, int v){
    if(d[u] < d[v]) swap(u, v);
 
    int diff = d[u] - d[v];
    if(diff){
        for(int i = k_LOG_N - 1; i >= 0; --i){
            if(diff & (1 << i)){
                u = up[i][u];
            }
        }
    }
 
    if(u == v) return u;
 
    for(int i = k_LOG_N - 1; i >= 0; --i){
        if(up[i][u] != up[i][v]){
            u = up[i][u];
            v = up[i][v];
        }
    }
 
    return up[0][u];
}
 
int main(){
    ios::sync_with_stdio(false);
    cin.tie(NULL);
    
    //cout << (sizeof(up) + sizeof(p) + sizeof(sz) + sizeof(suffix) + sizeof(root) + sizeof(not_critical) + sizeof(adj) + sizeof(edges) + 6 * sizeof(int) * k_N) / 1024 / 1024 << endl;
 
    cin >> n >> m;
 
    for(int i = 1; i <= n; ++i){
        p[i] = i;
        sz[i] = 1;
        root[i] = i;
        suffix[i] = 0;
        d[i] = 0;
 
        //for(int j = 0; j < k_LOG_N; ++j)
        //    up[j][i] = i;
    }
 
    for(int i = 0; i < m; ++i){
        int u, v;
        cin >> u >> v;
 
        if(unite(u, v)){
            edges.push_back({u, v});
            adj[u].push_back(edges.size() - 1);
            adj[v].push_back(edges.size() - 1);
        }
        else{
            int lca = get_lca(u, v);
            suffix[lca] -= 2;
            suffix[u]++;
            suffix[v]++;
        }
    }
 
    for(int i = 1; i <= n; ++i)
        if(i == find_p(i))
            dfs(root[i]);
 
    for(int i = 0; i < edges.size(); ++i)
        if(!not_critical[i])
            cout << edges[i].first << " " << edges[i].second << "\n";
}

Compilation message

pipes.cpp: In function 'int main()':
pipes.cpp:129:22: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
     for(int i = 0; i < edges.size(); ++i)
                    ~~^~~~~~~~~~~~~~
# 결과 실행 시간 메모리 Grader output
1 Correct 2 ms 2816 KB Output is correct
2 Correct 3 ms 2816 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 7 ms 3456 KB Output is correct
2 Correct 7 ms 3456 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 181 ms 3832 KB Output is correct
2 Correct 175 ms 3960 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 329 ms 4728 KB Output is correct
2 Correct 382 ms 4708 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 583 ms 6464 KB Output is correct
2 Correct 515 ms 7264 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1077 ms 12016 KB Output is correct
2 Correct 958 ms 11888 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1815 ms 13072 KB Output is correct
2 Correct 1715 ms 13156 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 2854 ms 16048 KB Output is correct
2 Runtime error 2694 ms 56804 KB Memory limit exceeded
# 결과 실행 시간 메모리 Grader output
1 Correct 3261 ms 15900 KB Output is correct
2 Runtime error 3402 ms 65536 KB Memory limit exceeded
# 결과 실행 시간 메모리 Grader output
1 Correct 3592 ms 14724 KB Output is correct
2 Correct 4093 ms 15368 KB Output is correct