QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#608830#9424. Stop the Castle 2ucup-team3877RE 1ms3604kbC++2010.3kb2024-10-04 05:03:362024-10-04 05:03:37

Judging History

This is the latest submission verdict.

  • [2024-10-04 05:03:37]
  • Judged
  • Verdict: RE
  • Time: 1ms
  • Memory: 3604kb
  • [2024-10-04 05:03:36]
  • Submitted

answer

#include <bits/stdc++.h>
using namespace std;
#define all(v) (v).begin(),(v).end()

#define rep(i, n) for(int i=0;i<n;i++)
#define foa(e, v) for(auto& e : v)
using ll = long long;
const ll MOD7 = 1000000007, MOD998 = 998244353, INF = (1LL << 60);
#define dout(a) cout<<fixed<<setprecision(10)<<a<<endl;

namespace atcoder {

namespace internal {

template <class T> struct simple_queue {
    std::vector<T> payload;
    int pos = 0;
    void reserve(int n) { payload.reserve(n); }
    int size() const { return int(payload.size()) - pos; }
    bool empty() const { return pos == int(payload.size()); }
    void push(const T& t) { payload.push_back(t); }
    T& front() { return payload[pos]; }
    void clear() {
        payload.clear();
        pos = 0;
    }
    void pop() { pos++; }
};

}  // namespace internal

}  // namespace atcoder

namespace atcoder {

template <class Cap> struct mf_graph {
  public:
    mf_graph() : _n(0) {}
    mf_graph(int n) : _n(n), g(n) {}

    int add_edge(int from, int to, Cap cap) {
        assert(0 <= from && from < _n);
        assert(0 <= to && to < _n);
        assert(0 <= cap);
        int m = int(pos.size());
        pos.push_back({from, int(g[from].size())});
        int from_id = int(g[from].size());
        int to_id = int(g[to].size());
        if (from == to) to_id++;
        g[from].push_back(_edge{to, to_id, cap});
        g[to].push_back(_edge{from, from_id, 0});
        return m;
    }

    struct edge {
        int from, to;
        Cap cap, flow;
    };

    edge get_edge(int i) {
        int m = int(pos.size());
        assert(0 <= i && i < m);
        auto _e = g[pos[i].first][pos[i].second];
        auto _re = g[_e.to][_e.rev];
        return edge{pos[i].first, _e.to, _e.cap + _re.cap, _re.cap};
    }
    std::vector<edge> edges() {
        int m = int(pos.size());
        std::vector<edge> result;
        for (int i = 0; i < m; i++) {
            result.push_back(get_edge(i));
        }
        return result;
    }
    void change_edge(int i, Cap new_cap, Cap new_flow) {
        int m = int(pos.size());
        assert(0 <= i && i < m);
        assert(0 <= new_flow && new_flow <= new_cap);
        auto& _e = g[pos[i].first][pos[i].second];
        auto& _re = g[_e.to][_e.rev];
        _e.cap = new_cap - new_flow;
        _re.cap = new_flow;
    }

    Cap flow(int s, int t) {
        return flow(s, t, std::numeric_limits<Cap>::max());
    }
    Cap flow(int s, int t, Cap flow_limit) {
        assert(0 <= s && s < _n);
        assert(0 <= t && t < _n);
        assert(s != t);

        std::vector<int> level(_n), iter(_n);
        internal::simple_queue<int> que;

        auto bfs = [&]() {
            std::fill(level.begin(), level.end(), -1);
            level[s] = 0;
            que.clear();
            que.push(s);
            while (!que.empty()) {
                int v = que.front();
                que.pop();
                for (auto e : g[v]) {
                    if (e.cap == 0 || level[e.to] >= 0) continue;
                    level[e.to] = level[v] + 1;
                    if (e.to == t) return;
                    que.push(e.to);
                }
            }
        };
        auto dfs = [&](auto self, int v, Cap up) {
            if (v == s) return up;
            Cap res = 0;
            int level_v = level[v];
            for (int& i = iter[v]; i < int(g[v].size()); i++) {
                _edge& e = g[v][i];
                if (level_v <= level[e.to] || g[e.to][e.rev].cap == 0) continue;
                Cap d =
                    self(self, e.to, std::min(up - res, g[e.to][e.rev].cap));
                if (d <= 0) continue;
                g[v][i].cap += d;
                g[e.to][e.rev].cap -= d;
                res += d;
                if (res == up) break;
            }
            return res;
        };

        Cap flow = 0;
        while (flow < flow_limit) {
            bfs();
            if (level[t] == -1) break;
            std::fill(iter.begin(), iter.end(), 0);
            while (flow < flow_limit) {
                Cap f = dfs(dfs, t, flow_limit - flow);
                if (!f) break;
                flow += f;
            }
        }
        return flow;
    }

    std::vector<bool> min_cut(int s) {
        std::vector<bool> visited(_n);
        internal::simple_queue<int> que;
        que.push(s);
        while (!que.empty()) {
            int p = que.front();
            que.pop();
            visited[p] = true;
            for (auto e : g[p]) {
                if (e.cap && !visited[e.to]) {
                    visited[e.to] = true;
                    que.push(e.to);
                }
            }
        }
        return visited;
    }

  private:
    int _n;
    struct _edge {
        int to, rev;
        Cap cap;
    };
    std::vector<std::pair<int, int>> pos;
    std::vector<std::vector<_edge>> g;
};

}  // namespace atcoder


using namespace atcoder;

void solve() {
    int n, m, k; cin >> n >> m >> k;
    map<int, int> mp1;
    vector<int> x1(n), y1(n), x2(n), y2(n);
    rep(i, n) {
        cin >> x1[i] >> y1[i];
        mp1[x1[i]] ++;
        mp1[y1[i]] ++;
    }
    rep(i, m) {
        cin >> x2[i] >> y2[i];
        mp1[x2[i]] ++;
        mp1[y2[i]] ++;
    }
    int id = 0;
    for(auto [x, y] : mp1) {
        mp1[x] = id ++;
    }
    rep(i, n) {
        x1[i] = mp1[x1[i]];
        y1[i] = mp1[y1[i]];
    }
    rep(i, m) {
        x2[i] = mp1[x2[i]];
        y2[i] = mp1[y2[i]];
    }
    
    vector<vector<pair<int, int>>> vec(m);
    vector<set<int>> X(id), Y(id);
    vector<set<pair<int, int>>> Xs(id), Ys(id);
    rep(i, n) {
        X[x1[i]].insert(y1[i]);
        Y[y1[i]].insert(x1[i]);
        Xs[x1[i]].insert({y1[i], i});
        Ys[y1[i]].insert({x1[i], i});
    }
    rep(i, m) {
        Xs[x2[i]].insert({y2[i], i + n});
        Ys[y2[i]].insert({x2[i], i + n});
    }
    int ans = 0;
    map<pair<int, int>, int> mp;
    rep(i, id) {
        foa(e, X[i]) {
            auto it = X[i].upper_bound(e);
            if(it == X[i].end()) continue;
            int r = *it;
            auto itrl = Xs[i].lower_bound(make_pair(e, -1));
            auto itrr = Xs[i].lower_bound(make_pair(r, -1));
            auto itr = itrl;
            itr ++;
            int i1 = itrl->second;
            int i2 = itrr->second;
            if(i1 > i2) swap(i1, i2);
            int cnt = 0;
            for(; itr != itrr; itr ++) {
                cnt ++;
                mp[{i1, i2}] ++;
                vec[itr->second - n].push_back({i1, i2});
            }
            if(!cnt) ans ++;
        }
        foa(e, Y[i]) {
            auto it = Y[i].upper_bound(e);
            if(it == Y[i].end()) continue;
            int r = *it;
            auto itrl = Ys[i].lower_bound(make_pair(e, -1));
            auto itrr = Ys[i].lower_bound(make_pair(r, -1));
            auto itr = itrl;
            itr ++;
            int i1 = itrl->second;
            int i2 = itrr->second;
            if(i1 > i2) swap(i1, i2);
            int cnt = 0;
            for(; itr != itrr; itr ++) {
                cnt ++;
                mp[{i1, i2}] ++;
                vec[itr->second - n].push_back({i1, i2});
            }
            if(!cnt) ans ++;
        }
    }
    
    id = 0;
    for(auto [x, y] : mp) {
        mp[x] = id ++;
    }
    vector<vector<int>> v(id);
    vector<int> cnt(id, 0);
    vector<vector<int>> lis(id);
    map<pair<int, int>, int> v2e;
    vector<int> del0, del1, del2;
    rep(i, m) {
        int sz = vec[i].size();
        if(sz == 0) {
            del0.push_back(i + 1);
        } else if(sz == 1) {
            cnt[mp[vec[i][0]]] ++;
            lis[mp[vec[i][0]]].push_back(i);
        } else {
            int a = mp[vec[i][0]];
            int b = mp[vec[i][1]];
            v[a].push_back(b);
            v[b].push_back(a);
            v2e[{a, b}] = i;
            v2e[{b, a}] = i;
        }
    }
    
    mf_graph<int> G(id + 2);
    vector<int> seen(id, -1);
    auto dfs = [&](auto dfs, int now) -> void {
        foa(e, v[now]) {
            if(seen[e] == -1) {
                seen[e] = seen[now] ^ 1;
                dfs(dfs, e);
            }
        }
    };
    rep(i, id) if(seen[i] == -1) {
        seen[i] = 0;
        dfs(dfs, i);
    }
    int s = id, t = id + 1;
    rep(i, id) {
        if(seen[i]) {
            G.add_edge(s, i, 1);
            foa(e, v[i]) {
                G.add_edge(i, e, 1);
            }
        } else {
            G.add_edge(i, t, 1);
        }
    }
    G.flow(s, t);
    auto ret = G.edges();
    set<int> inc, mushi;
    foa(e, ret) if(e.flow) {
        if(e.from != s and e.to != t) {
            inc.insert(e.from);
            inc.insert(e.to);
            mushi.insert(v2e[{e.from, e.to}]);
            del2.push_back(v2e[{e.from, e.to}] + 1);
        }
    }
    rep(i, id) {
        if((int)v[i].size()) {
            foa(e, lis[i]) del0.push_back(e + 1);
            if(!inc.count(i)) {
                int x = v2e[{i, v[i][0]}];
                mushi.insert(x);
                del1.push_back(x + 1);
            }
        } else {
            int sz = lis[i].size();
            rep(j, sz - 1) del0.push_back(lis[i][j] + 1);
            del1.push_back(lis[i].back() + 1);
        }
    }
    rep(i, id) foa(e, v[i]) if(!mushi.count(v2e[{i, e}])) {
        mushi.insert(v2e[{i, e}]);
        del0.push_back(v2e[{i, e}] + 1);
    }
    int sz0 = del0.size();
    int sz1 = del1.size();
    if(k <= sz0) {
        cout << ans << endl;
        rep(i, k) cout << del0[i] << " ";
        cout << endl;
    } else if(k <= sz0 + sz1) {
        cout << ans + k - sz0 << endl;
        foa(e, del0) cout << e << " ";
        k -= sz0;
        rep(i, k) cout << del1[i] << " ";
        cout << endl;
    } else {
        cout << ans + sz1 + (k - sz0 - sz1) * 2 << endl;
        foa(e, del0) cout << e << " ";
        foa(e, del1) cout << e << " ";
        k -= sz0 + sz1;
        rep(i, k) cout << del2[i] << " ";
        cout << endl;
    }
}

int main() {
    cin.tie(0);
    ios::sync_with_stdio(false);
    
    int t;
    cin >> t;
    rep(i, t) solve();
    return 0;
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 1ms
memory: 3604kb

input:

3
8 6 4
1 3
2 1
2 6
4 1
4 7
6 1
6 3
6 6
2 3
3 1
4 3
4 6
5 2
6 4
3 2 1
10 12
10 10
10 11
1 4
1 5
1 3 2
1 1
2 1
2 2
2 3

output:

4
5 3 2 6 
2
1 
0
1 2 

result:

ok ok 3 cases (3 test cases)

Test #2:

score: -100
Runtime Error

input:

1224
11 17 14
7 3
4 2
8 13
3 15
3 4
5 11
10 2
3 3
8 6
7 11
2 3
10 4
1 3
12 1
2 5
11 9
11 6
11 10
8 15
1 5
9 14
4 11
1 6
10 7
7 6
11 4
8 4
1 11
18 3 2
14 8
2 14
13 13
9 12
14 12
5 6
8 1
10 5
8 6
8 9
6 6
7 5
12 11
6 11
13 5
1 10
7 6
14 5
6 15
2 4
11 1
1 6 4
14 14
13 9
9 3
10 12
7 5
8 13
9 14
1 9 8
4 9...

output:

7
1 2 3 4 5 6 7 8 9 10 11 12 13 15 

result: