Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
63 changes: 0 additions & 63 deletions library/graphs/hopcroft_karp.hpp

This file was deleted.

13 changes: 13 additions & 0 deletions library/graphs/min_vertex_cover.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#include "../../kactl/content/graph/HopcroftKarp.h"
pair<vi, vi> cover(const vector<vi>& g, vi& r) {
int n = sz(g), t = 0;
vi cl(n), cr(sz(r)), q(n);
for (int u : r)
if (u != -1) cl[u] = 1;
rep(i, 0, n) if (!cl[i]) q[t++] = i;
rep(i, 0, t) for (int v : g[q[i]]) {
cr[v] = 1;
if (r[v] != -1 && cl[r[v]]) cl[q[t++] = r[v]] = 0;
}
return {cl, cr};
}
40 changes: 12 additions & 28 deletions tests/library_checker_aizu_tests/graphs/hopcroft_karp_aizu.test.cpp
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#define PROBLEM \
"https://judge.u-aizu.ac.jp/onlinejudge/description.jsp?id=GRL_7_A"
#include "../template.hpp"
#include "../../../library/graphs/hopcroft_karp.hpp"
#include "../../../library/graphs/min_vertex_cover.hpp"
int main() {
cin.tie(0)->sync_with_stdio(0);
int l, r, m;
Expand All @@ -14,34 +14,18 @@ int main() {
adj[u].push_back(v);
edges.emplace_back(u, v);
}
hopcroft_karp res(adj, r);
cout << res.m_sz << '\n';
// asserting correctness of both to_r, and to_l
int size_l = 0;
for (int i = 0; i < l; i++) {
if (res.to_r[i] != -1) {
size_l++;
int node_r = res.to_r[i];
assert(res.to_l[node_r] == i);
}
}
vi ri(r, -1);
int size_matching = hopcroftKarp(adj, ri);
auto [mvc_l, mvc_r] = cover(adj, ri);
int size_r = 0;
for (int i = 0; i < r; i++) {
if (res.to_l[i] != -1) {
size_r++;
int node_l = res.to_l[i];
assert(res.to_r[node_l] == i);
}
}
assert(size_l == res.m_sz);
assert(size_r == res.m_sz);
for (int i = 0; i < r; i++)
if (ri[i] != -1) size_r++;
assert(size_r == size_matching);
// asserting found min vertex cover is correct
int cnt =
accumulate(begin(res.mvc_l), end(res.mvc_l), 0) +
accumulate(begin(res.mvc_r), end(res.mvc_r), 0);
assert(cnt == res.m_sz); // size of min vertex cover
// == size of max matching
for (auto [u, v] : edges)
assert(res.mvc_l[u] || res.mvc_r[v]);
int cnt = accumulate(begin(mvc_l), end(mvc_l), 0) +
accumulate(begin(mvc_r), end(mvc_r), 0);
assert(cnt == size_matching);
for (auto [u, v] : edges) assert(mvc_l[u] || mvc_r[v]);
cout << size_matching << '\n';
return 0;
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#define PROBLEM \
"https://judge.yosupo.jp/problem/bipartitematching"
#include "../template.hpp"
#include "../../../library/graphs/hopcroft_karp.hpp"
#include "../../../library/graphs/min_vertex_cover.hpp"
int main() {
cin.tie(0)->sync_with_stdio(0);
int l, r, m;
Expand All @@ -14,36 +14,21 @@ int main() {
adj[u].push_back(v);
edges.emplace_back(u, v);
}
hopcroft_karp res(adj, r);
cout << res.m_sz << '\n';
// asserting correctness of both to_r, and to_l (as
// well as printing answer)
int size_l = 0;
for (int i = 0; i < l; i++) {
if (res.to_r[i] != -1) {
size_l++;
int node_r = res.to_r[i];
cout << i << " " << node_r << '\n';
assert(res.to_l[node_r] == i);
}
}
vi ri(r, -1);
int m_sz = hopcroftKarp(adj, ri);
auto [mvc_l, mvc_r] = cover(adj, ri);
cout << m_sz << '\n';
int size_r = 0;
for (int i = 0; i < r; i++) {
if (res.to_l[i] != -1) {
if (ri[i] != -1) {
size_r++;
int node_l = res.to_l[i];
assert(res.to_r[node_l] == i);
cout << ri[i] << ' ' << i << '\n';
}
}
assert(size_l == res.m_sz);
assert(size_r == res.m_sz);
// asserting found min vertex cover is correct
int cnt =
accumulate(begin(res.mvc_l), end(res.mvc_l), 0) +
accumulate(begin(res.mvc_r), end(res.mvc_r), 0);
assert(cnt == res.m_sz); // size of min vertex cover
// == size of max matching
for (auto [u, v] : edges)
assert(res.mvc_l[u] || res.mvc_r[v]);
assert(size_r == m_sz);
int cnt = accumulate(begin(mvc_l), end(mvc_l), 0) +
accumulate(begin(mvc_r), end(mvc_r), 0);
assert(cnt == m_sz);
for (auto [u, v] : edges) assert(mvc_l[u] || mvc_r[v]);
return 0;
}
Loading