Cod sursa(job #2962758)

Utilizator NFJJuniorIancu Ivasciuc NFJJunior Data 9 ianuarie 2023 07:04:01
Problema Cuplaj maxim in graf bipartit Scor 90
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.24 kb
#include <bits/stdc++.h>
using namespace std;
ifstream f("cuplaj.in");
ofstream g("cuplaj.out");
#define cin f
#define cout g

int N, M, E;
//	the matrix capacity stores the residual network capacity
int n;
vector<int> parent;
vector<unordered_map<int, int>> capacity;
vector<unordered_map<int, int>> adj;

bool bfs(int s, int t)
{
	fill(parent.begin(), parent.end(), -1);
	parent[s] = -2;

	queue<int> Q;
	Q.push(s);

	while(! Q.empty())
	{
		int cur = Q.front();
		Q.pop();

		for(auto &edge : capacity[cur])
		{
			if(parent[edge.first] == -1 and edge.second != 0)
			{
				parent[edge.first] = cur;

				if(edge.first == t)
					return true;

				Q.push(edge.first);
			}
		}
	}

	return false;
}

int maxflow(int s, int t)
{
	int flow = 0;

	while(bfs(s, t))
	{
		for(auto &edge : capacity[t])
		{
			int cur = edge.first;
			if(capacity[cur][t] == 0 || parent[cur] == -1)
				continue;

			int new_flow = INT_MAX;
			new_flow = min(new_flow, capacity[cur][t]);

			while(cur != s)
			{
				int prev = parent[cur];
				new_flow = min(new_flow, capacity[prev][cur]);
				if(new_flow == 0)
					break;
				cur = prev;
			}

			if(new_flow == 0)
				continue;
			flow += new_flow;

			cur = edge.first;
			capacity[cur][t] -= new_flow;
			capacity[t][cur] += new_flow;

			while(cur != s)
			{
				int prev = parent[cur];
				capacity[prev][cur] -= new_flow;
				capacity[cur][prev] += new_flow;
				cur = prev;
			}
		}
	}

	return flow;
}

int main()
{
	cin >> N >> M >> E;
	n = N + M + 2;
	parent.resize(n + 1);
	capacity.resize(n + 1);
	adj.resize(n + 1);
	
	for(int i = 1; i <= E; i++)
	{
		int x, y;
		cin >> x >> y;
		adj[x][y + N] = 1;
		capacity[x][y + N] = 1;
		if(capacity[y + N].find(x) == capacity[y + N].end())
			capacity[y + N][x] = 0;
	}

	int s, t;
	s = n - 1, t = n;

	for(int i = 1; i <= N; i++)
	{

		adj[s][i] = 1;
		capacity[s][i] = 1;
		capacity[i][s] = 0;
	}

	for(int i = 1; i <= M; i++)
	{
		adj[i + N][t];
		capacity[i + N][t] = 1;
		capacity[t][i + N] = 0;
	}

	cout<<maxflow(s, t)<<'\n';

	for(int i = 1; i <= N; i++)
		for(auto it : adj[i])
			if(capacity[i][it.first] == 0)
				cout<<i<<' '<<it.first - N<<'\n';

	return 0;
}