Cod sursa(job #2956474)

Utilizator dragosteleagaDragos Teleaga dragosteleaga Data 19 decembrie 2022 16:44:23
Problema Cuplaj maxim in graf bipartit Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.22 kb
#include <bits/stdc++.h>
#define inf INT_MAX
using namespace std;
ifstream f("cuplaj.in");
ofstream g("cuplaj.out");
int n, m, e, a, b;
vector<int> la[20001];
queue<int> q;
int dist[20001];
int stanga[20001], dreapta[20001];

bool bfs() {
    //primul layer de nod uri ii setam distanta cu 0
    for (int i = 1; i <= n; i++)
        if (!dreapta[i]) {
            //daca e liber,il bagam in coada
            q.push(i);
            dist[i] = 0;
        }
        else//notam distanta cu infinit ca sa fie luat data urmatoare
            dist[i] = inf;
        dist[0] = inf;
    //q o sa aiba nodurile de stanga
    while (!q.empty()) {
        int node = q.front();
        q.pop();
        //daca nodul nu e 0 si poate aduce un short path catre 0
        if (dist[node] < dist[0])//daca il cuplez pe 0 cu cineva => am gasit cuplaj din lant de lungime minimia
        {
            //parcurgem toti vecinii lui node
            for (auto next: la[node]) {
                if (dist[stanga[next]] == inf)//next e cuplat cu stanga[next]
                {
                    dist[stanga[next]] = 1 + dist[node];
                    q.push(stanga[next]);
                }
            }
        }
    }
    return dist[0] != inf; //lant
}
//returneaza adevarat daca e un augmenting path incepand cu nodul liber node
bool dfs(int node)
{
    if(node != 0)
    {
        for(auto next : la[node])
            if(1 + dist[node] == dist[stanga[next]] && dfs(stanga[next]))
            {

                stanga[next] = node;
                dreapta[node] = next;
                return true;
            }
        //nu am gasit path
        dist[node] = inf;
        return false;
    }
    return true;
}
int maxmatch()
{
    int ans = 0;
    while(bfs())
    {
        for(int i = 1 ; i <= n ; i++)
            if(!dreapta[i] && dfs(i))
                ans++;
    }
    return ans;
}
int main(){
    f >> n >> m >> e;
    fill(stanga, stanga + 20001, 0);
    fill(dreapta, dreapta + 20001, 0);
    for(int i = 1 ; i <= e ; i++)
    {
        f >> a >> b;
        la[a].push_back(b);
    }
    g << maxmatch() << '\n';
    for(int i = 1 ; i <= m ; i++)
        if(stanga[i])
            g << stanga[i] << ' ' << i << '\n';
    return 0;
}
//algoritmul lui Hopcroft Karp O(sqrt(VE))