Cod sursa(job #1451523)

Utilizator MciprianMMciprianM MciprianM Data 17 iunie 2015 14:35:56
Problema Cuplaj maxim in graf bipartit Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.1 kb
#include <fstream>
#include <queue>
#include <vector>
#include <cstring>
  
using namespace std;
  
static const int MAXN = 10009;
int n, m;
vector<int> G[MAXN];
int matchForL[MAXN];
int matchForR[MAXN];
bool u[MAXN];
int dist[MAXN];
 
void bfs()
{
    int nod;
    memset(u, 0, sizeof u);
    memset(dist, 0x3F, sizeof dist);
    queue<int> q;
    for(int i = 1; i <= n; i++)
    {
        if(!matchForL[i])
        {
            u[i] = true;
            q.push(i);
            dist[i] = 0;
        }
    }
    while(!q.empty())
    {
        nod = q.front();
        q.pop();
        for(int i = 0, l = G[nod].size(); i < l; i++)
        {
            int vec = matchForR[G[nod][i]];
			if(!u[vec])
			{
				dist[vec] = dist[nod] + 1;
				u[vec] = true;
				if(dist[vec] < dist[0])
				{
					q.push(vec);
				}
			}
        }
    }
}
 
bool dfs(int who)
{
    u[who] = true;
    for(int i = 0, l = G[who].size(); i < l; i++)
    {
        int vec = matchForR[G[who][i]];
        if(!vec || (!u[vec] && dist[vec] == dist[who] + 1 && dfs(vec)))
        {
            matchForL[who] = G[who][i];
            matchForR[G[who][i]] = who;
            return true;
        }
    }
    return false;
}
  
int main()
{
    int e, x, y;
    ifstream f("cuplaj.in");
    f >> n >> m >> e;
    for(int i = 0; i < e; i++)
    {
        f >> x >> y;
        G[x].push_back(y);
    }
    f.close();
    bool ok = true;
    do
    {
        ok = false;
        bfs();
        memset(u, 0, sizeof u);
        for(int i = 1; i <= n; i++)
        {
            if(!matchForL[i])
            {
                ok = dfs(i) || ok;
            }
        }
    } while(ok);
    vector<pair<int, int> > ans;
    for(int i = 1; i <= n; i++)
    {
        if(matchForL[i])
        {
            ans.push_back(pair<int, int>(i, matchForL[i]));
        }
    }
    ofstream g("cuplaj.out");
    g << ans.size() << '\n';
    for(int i = 0, l = ans.size(); i < l; i++)
    {
        g << ans[i].first << ' ' << ans[i].second << '\n';
    }
    g.close();
    return 0;
}