Pagini recente » Borderou de evaluare (job #3357881) | Autentificare | Cod sursa (job #428403) | Cod sursa (job #3339232) | Cod sursa (job #3357779)
#include <iostream>
#include <vector>
#include <queue>
#include <algorithm>
struct Network {
private:
std::vector<std::vector<int>> adj;
std::vector<std::vector<int>> capacity;
std::vector<std::vector<int>> flow;
std::vector<int> parent;
int size;
int augment(int source, int target) {
parent.assign(size + 1, -1);
parent[source] = -2;
std::queue<std::pair<int, int>> q;
q.emplace(source, 1e9);
while (!q.empty()) {
int node = q.front().first;
int flow_val = q.front().second;
q.pop();
for (int neighbor : adj[node]) {
if (parent[neighbor] == -1 && capacity[node][neighbor] - flow[node][neighbor] > 0) {
parent[neighbor] = node;
int new_flow = std::min(flow_val, capacity[node][neighbor] - flow[node][neighbor]);
if (neighbor == target) {
return new_flow;
}
q.emplace(neighbor, new_flow);
}
}
}
return 0;
}
public:
explicit Network(int n) : size(n) {
adj.resize(size + 1);
capacity.resize(size + 1, std::vector<int>(size + 1, 0));
flow.resize(size + 1, std::vector<int>(size + 1, 0));
}
void add_edge(int x, int y, int cap) {
adj[x].push_back(y);
adj[y].push_back(x);
capacity[x][y] = cap;
}
int max_flow(int source, int target) {
int total_flow = 0;
int flow_val;
while ((flow_val = augment(source, target)) != 0) {
total_flow += flow_val;
int cur = target;
while (cur != source) {
int prev = parent[cur];
flow[prev][cur] += flow_val;
flow[cur][prev] -= flow_val;
cur = prev;
}
}
return total_flow;
}
const std::vector<std::vector<int>>& get_flow() const {
return flow;
}
};
int main() {
freopen("cuplaj.in", "r", stdin);
freopen("cuplaj.out", "w", stdout);
std::ios_base::sync_with_stdio(false);
std::cin.tie(nullptr);
std::cout.tie(nullptr);
int n, m, k;
std::cin >> n >> m >> k;
Network network(n + m + 2);
int source = 0, sink = n + m + 1;
for (int i = 1; i <= n; ++i) {
network.add_edge(source, i, 1);
}
for (int i = 1; i <= m; ++i) {
network.add_edge(n + i, sink, 1);
}
for (int i = 0; i < k; ++i) {
int x, y;
std::cin >> x >> y;
network.add_edge(x, n + y, 1);
}
std::cout << network.max_flow(source, sink) << '\n';
auto& flow = network.get_flow();
for (int i = 1; i <= n; ++i) {
for (int j = 1; j <= m; ++j) {
if (flow[i][n + j] > 0) {
std::cout << i << " " << j << '\n';
}
}
}
return 0;
}