Cod sursa(job #2960286)

Utilizator ioanatcioana t ioanatc Data 3 ianuarie 2023 22:55:30
Problema Cuplaj maxim in graf bipartit Scor 50
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.47 kb
#include<iostream>
#include<fstream>
#include<queue>
using namespace std;
#define Max 20000

int N, M, E, x, y, cuplaj;

bool graf_rez[Max][Max];
bool vizitat[Max];
int tata[Max];

void citesteDate();
void scrieRezultat();

bool lantBFS(){
    // initializare date
    for(int i = 0; i <= N+M+1; i++)
        vizitat[i] = 0, tata[i] = -1;

    queue<int> coada;
    coada.push(0);
    vizitat[0] = 1;

    while(!coada.empty()){
        int curent = coada.front();
        coada.pop();

        if(curent == N+M+1) return true;

        for(int nod = 1; nod <= N+M+1; nod++){
            if(!vizitat[nod] && graf_rez[curent][nod]){

                vizitat[nod] = 1;
                tata[nod] = curent;
                coada.push(nod);
            }
        }
    }
    return false;
}
int main(){
    citesteDate();
    
    // construiesc reteaua de transport
    for(int nod = 0; nod <= N; nod ++)
        graf_rez[0][nod] = 1;

    for(int nod = 1; nod <=M; nod ++)
        graf_rez[N + nod][N+M+1] = 1;
    
    while (lantBFS())
    {
        for(int nod = 1; nod < N+M+1; nod ++){

            if(vizitat[nod] && graf_rez[nod][N+M+1]){
                int flux_curent = graf_rez[nod][N+M+1];

                int auxiliar = nod;
                while(tata[auxiliar] != -1){
                    flux_curent = min(flux_curent, (int)graf_rez[tata[auxiliar]][auxiliar]);
                    auxiliar = tata[auxiliar];
                }
                if(flux_curent){
                    // actualizam tatal nodului N+M+1(final) in lantul curent
                    tata[N+M+1] = nod;
                    // inregistram lantul curent in graful rezidual
                    int auxiliar = N+M+1;

                    while(tata[auxiliar] != -1){
                        graf_rez[ tata[auxiliar] ][ auxiliar ] -= 1;
                        graf_rez[ auxiliar ][ tata[auxiliar] ] += 1;
                        auxiliar = tata[auxiliar];
                    }
                    cuplaj+=1;
                }
            }
        }
    }

    scrieRezultat();
    return 0;
}
void citesteDate(){
    ifstream f("cuplaj.in");
    
    f>>N>>M>>E;
    while(f>>x>>y){
        graf_rez[x][N+y] = 1;
    }
}
void scrieRezultat(){
    ofstream g ("cuplaj.out");
    g<<cuplaj<<"\n";

    for(int i = 1; i<=N; i++){
        for(int j = N+1; j<=M+N; j++)
            if(graf_rez[j][i])
                g<<i<<" "<<j-N<<"\n";
    }
}