Cod sursa(job #2735817)

Utilizator Rares31100Popa Rares Rares31100 Data 2 aprilie 2021 20:48:58
Problema Cuplaj maxim in graf bipartit Scor 14
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.97 kb
#include <bits/stdc++.h>

using namespace std;

ifstream fin("cuplaj.in");
ofstream fout("cuplaj.out");
int n, m, e, rezultat;
int pereche[20001];
int vf[200001], urm[200001], last[20001];

void adauga(int from, int to)
{
	static int nr = 0;
	vf[++nr] = to;
	urm[nr] = last[from];
	last[from] = nr;
}

int nivel[20001], drum[20001];
bitset <20001> used;
bool dfs(int nod, int lung = 1)
{
	drum[lung] = nod;

	if(nivel[nod] == 1)
	{
		for(int i = 1; i <= lung - 1; i += 2)
		{
			pereche[ drum[i] ] = drum[i + 1];
			pereche[ drum[i + 1] ] = drum[i];
		}

		nivel[nod] = 0;
		rezultat++;
		return true;
	}

	bool found = false;
	for(int i = last[nod]; i && !found; i = urm[i])
		if(nivel[ vf[i] ] && nivel[ vf[i] ] < nivel[nod])
			found = max(found, dfs(vf[i], lung + 1));

	if(found)
		nivel[nod] = 0;

	return found;
}
bool bfs()
{
	queue <int> q;
	bool found = false;

	for(int i = 1; i <= n + m; i++)
	{
		nivel[i] = 0;
		used[i] = 0;
	}

	for(int i = 1; i <= n; i++)
		if(!pereche[i])
		{
			q.push(i);
			nivel[i] = 1;
			used[i] = 1;
		}

	while(!q.empty())
	{
		int nod = q.front();
		q.pop();

		if(nod > n && pereche[nod] && !used[ pereche[nod] ])
		{
			used[ pereche[nod] ] = 1;
			nivel[ pereche[nod] ] = nivel[nod] + 1;
			q.push(pereche[nod]); 
		}
		else if(nod > n)
		{
			found = max(found, dfs(nod));
		}
		else
		{
			for(int i = last[nod]; i; i = urm[i])
				if(!used[ vf[i] ])
				{
					used[ vf[i] ] = 1;
					nivel[ vf[i] ] = nivel[nod] + 1;
					q.push(vf[i]);
				}
		}
	}

	return found;
}

int main()
{
	fin >> n >> m >> e;
	for(int k = 1, i, j; k <= e; k++)
	{
		fin >> i >> j;
		j += n;
		adauga(i, j);
		adauga(j, i);

		if(!pereche[i] && !pereche[j])
		{
			pereche[i] = j;
			pereche[j] = i;
			rezultat++;
		}
	}
	
	while(bfs());
	fout << rezultat << '\n';

	for(int i = 1; i <= n; i++)
		if(pereche[i])
			fout << i << ' ' << pereche[i] - n << '\n';

	return 0;
}