1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115
| #include <bits/stdc++.h> using namespace std; const int inf = INT_MAX; pair<vector<vector<int>>, int> maxFlow(vector<vector<int>> adjMat, size_t s, size_t t) { auto residualMat = adjMat; bool flag = true; while (flag) { cout << "-----------------------" << endl; for (size_t i = 0; i < residualMat.size(); i++) { for (size_t j = 0; j < residualMat.size(); j++) cout << residualMat[i][j] << " "; cout << endl; } cout << "-----------------------" << endl; queue<size_t> q; vector<size_t> prev(residualMat.size(), adjMat.size() + 1); vector<int> flow(residualMat.size(), 0); vector<int> dis(residualMat.size(), inf); q.push(s); dis[s] = 0; flag = false; while (!q.empty()) { auto v = q.front(); q.pop(); if (prev[v] != adjMat.size() + 1) flow[v] = min(flow[prev[v]], residualMat[prev[v]][v]); else flow[v] = inf; if (v == t) { int min_cap = flow[v]; size_t p = v; cout << v << " "; while (prev[p] != adjMat.size() + 1) { cout << prev[p] << " "; residualMat[prev[p]][p] -= min_cap; residualMat[p][prev[p]] += min_cap; p = prev[p]; } cout << "- min_cap: " << min_cap << endl; flag = true; break; } else { for (size_t i = 0; i < adjMat.size(); i++) { if (dis[i] > 1 + dis[v] && !flow[i] && residualMat[v][i] > 0) { dis[i] = 1 + dis[v]; prev[i] = v; q.push(i); } } } } } size_t f_max = 0; for (size_t i = 0; i < adjMat.size(); i++) { f_max += residualMat[t][i]; }
return {residualMat, f_max}; }
set<pair<size_t, size_t>> minCut(vector<vector<int>> residualMat, vector<vector<int>> adjMat, int s, int t) { queue<size_t> q; vector<bool> vis(residualMat.size(), false); q.push(s); while (!q.empty()) { auto v = q.front(); q.pop(); vis[v] = true; for (size_t i = 0; i < residualMat.size(); i++) { if (residualMat[v][i] && !vis[i]) { q.push(i); } } }
set<size_t> S; set<size_t> T; for (size_t i = 0; i < adjMat.size(); i++) { if (vis[i]) S.emplace(i); else T.emplace(i); }
assert(S.count(s)); assert(T.count(t)); set<pair<size_t, size_t>> min_cut;
for (auto u : S) for (auto v : T) if (adjMat[u][v]) min_cut.emplace(u, v); return min_cut; }
int main() { vector<vector<int>> adjMat = { {0, 8, 7, 4, 0, 0, 0, 0}, {0, 0, 2, 0, 3, 9, 0, 0}, {0, 0, 0, 5, 0, 6, 0, 0}, {0, 0, 0, 0, 0, 7, 2, 0}, {0, 0, 0, 0, 0, 0, 0, 9}, {0, 0, 0, 0, 3, 0, 4, 5}, {0, 0, 0, 0, 0, 0, 0, 8}, {0, 0, 0, 0, 0, 0, 0, 0}}; auto [residualMat, f_max] = maxFlow(adjMat, 0, 7); auto min_cut = minCut(residualMat, adjMat, 0, 7); for (auto pr : min_cut) { cout << "(" << pr.first << ", " << pr.second << ")" << endl; } cout << f_max << endl; return 0; }
|