Cod sursa(job #2962486)

Utilizator dimi999Dimitriu Andrei dimi999 Data 8 ianuarie 2023 17:35:00
Problema Cuplaj maxim in graf bipartit Scor 40
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.11 kb
#include <fstream>
#include <vector>
#include <queue>
using namespace std;

ifstream fin("cuplaj.in");
ofstream fout("cuplaj.out");

int N, M, E;

int cap[1005][1005], flow[1005][1005], maxflow;

vector <int> v[1005];

bool viz[1005];
int path[1005];

bool bfs()
{
    fill(viz + 0, viz + N + M + 2, 0);

    queue <int> q;

    q.push(0);

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

        for(int i = 0; i < v[node].size(); i++)
            if(cap[node][v[node][i]] > flow[node][v[node][i]] && !viz[v[node][i]])
            {
                viz[v[node][i]] = true;
                q.push(v[node][i]);
                path[v[node][i]] = node;
            }
    }

    return viz[N + M + 1];
}

int main()
{
    fin >> N >> M >> E;

    for(int i = 1; i <= E; i++)
    {
        int x, y;

        fin >> x >> y;

        v[x].push_back(N + y);
        v[N + y].push_back(x);

        cap[x][N + y] = 1;
    }

    for(int i = 1; i <= N; i++) {
        v[i].push_back(0);
        v[0].push_back(i);

        cap[0][i] = 1;
    }

    for(int i = 1; i <= M; i++) {
        v[i + N].push_back(N + M + 1);
        v[N + M + 1].push_back(i + N);

        cap[i + N][N + M + 1] = 1;
    }


    while(bfs())
    {
        for(int i = 0; i < v[N + M + 1].size(); i++)
        {
            int ngb = v[N + M + 1][i];
            int toadd = cap[ngb][N + M + 1] - flow[ngb][N + M + 1];

            for(int it = ngb; it != 0; it = path[it])
                toadd = min(toadd, cap[path[it]][it] - flow[path[it]][it]);

            maxflow += toadd;

            flow[ngb][N + M + 1] += toadd;
            flow[N + M + 1][ngb] -= toadd;

            for(int it = ngb; it != 0; it = path[it])
            {
                flow[path[it]][it] += toadd;
                flow[it][path[it]] -= toadd;
            }
        }
    }

    fout << maxflow << '\n';

    for(int i = 1; i <= N; i++)
        for(int j = N + 1; j <= N + M; j++)
            if(flow[i][j] == 1)
                fout << i << " " << j - N<< '\n';

    return 0;
}