Cod sursa(job #2960157)

Utilizator Diana_14Diana Muscalu Diana_14 Data 3 ianuarie 2023 17:50:27
Problema Cuplaj maxim in graf bipartit Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.39 kb
#include <iostream>
#include <fstream>
#include <bits/stdc++.h>
#define inf INT_MAX

using namespace std;

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

int n, m, e;
int dist[20001];
int st[20001], dr[20001];
vector<int> list_ad[20001];
queue<int> q;


bool bfs() {
    ///primul layer de noduri ii setam distanta cu 0
    for (int i = 1; i <= n; i++)
        if (!dr[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 urm: list_ad[node]) {
                if (dist[st[urm]] == inf) ///urm e cuplat cu st[urm]
                {
                    dist[st[urm]] = 1 + dist[node];
                    q.push(st[urm]);
                }
            }
        }
    }
    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 urm : list_ad[node])
            if(1 + dist[node] == dist[st[urm]] && dfs(st[urm]))
            {

                st[urm] = node;
                dr[node] = urm;
                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(!dr[i] && dfs(i))
                ans++;
    }
    return ans;
}
int main(){

    f >> n >> m >> e;

    ///punem 0 in vectori
    fill(st, st + 20001, 0);
    fill(dr, dr + 20001, 0);

    /// formam lista de adiacenta
    for(int i = 1 ; i <= e ; i++)
    {
        int x, y;
        f >> x >> y;
        list_ad[x].push_back(y);
    }

    g << maxmatch() << '\n';

    for(int i = 1 ; i <= m ; i++)
        if(st[i])
            g << st[i] << ' ' << i << '\n';
    return 0;
}
///algoritmul lui Hopcroft Karp O(sqrt(VE))