Cod sursa(job #1393933)

Utilizator AeroHHorea Stefan AeroH Data 19 martie 2015 21:14:03
Problema Cuplaj maxim in graf bipartit Scor 90
Compilator cpp Status done
Runda Arhiva educationala Marime 2.27 kb
#include <fstream>
#include <vector>
#include <queue>
#include <unordered_map>
#include <cstring>
using namespace std;

ifstream f("cuplaj.in");
ofstream g("cuplaj.out");

#define N 20010
#define T 10000

int x,y,i,j,m,n,flow,p[N],pp[N],S=2*T+1,D=2*T+2,cap;
unordered_map<int,int> cost[N];
vector<int> v[N];
vector<pair<int,int> > edge;

int dfs()
{
    memset(p,0,sizeof(p));
    p[S]=-1;
    queue<int> q;
    q.push(S);
    while(q.size())
        {
            int x=q.front();
            q.pop();
            for(int i=0;i<v[x].size();++i)
                {
                    int y = v[x][i];
                    if (cost[x][y] > 0 && p[y] == 0)
                        {
                            p[y]=x;
                            q.push(y);
                        }
                }
        }
    return p[D];
}

int main()
{
    int M;
    f>>n>>m>>M;
    for(i=0;i<M;++i)
        {
            f>>x>>y;
            y+=T;
            v[x].push_back(y);
            v[y].push_back(x);
            cost[x][y]=1;
            edge.push_back(make_pair(x,y));
        }
    for(i=1;i<=n;++i)
        {
            v[S].push_back(i);
            cost[S][i]=1;
        }
    for(i=1;i<=m;++i)
        {
            v[D].push_back(i+T);
            v[i+T].push_back(D);
            cost[i+T][D]=1;
        }
    while(dfs())
        for(j=0;j<v[D].size();++j)
            {
                x=v[D][j];
                if (cost[x][D] > 0 && p[x] != 0)
                    {
                        cap=cost[x][D];

                        for (i=x;i!=S;i=p[i])cap=min(cap,cost[p[i]][i]);
                            if (cap == 0)
                                continue;
                        for (i=x;i!=S;i=p[i])
                            {
                                cost[p[i]][i]=0;
                                cost[i][p[i]]=1;
                            }
                        cost[x][D]=0;
                        ++flow;
                    }
            }

    g<<flow<<'\n';

    for(i=0;i<edge.size();++i)
        {
            if (cost[edge[i].second][edge[i].first])
                {
                    g<<edge[i].first<<" "<<edge[i].second-T<<'\n';
                }
        }
    return 0;
}