Cod sursa(job #2030542)

Utilizator xtreme77Patrick Sava xtreme77 Data 1 octombrie 2017 19:21:03
Problema Cuplaj maxim in graf bipartit Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 3.44 kb
#include <bits/stdc++.h>

using namespace std ;

class MaximalMatching {
public :
        MaximalMatching () {}
        MaximalMatching (vector< pair <int, int> > &edges, int st, int dr) {
            lftNodes = st ; 
            rgtNodes = dr ;
            gr.resize (st + 1) ; 
            lft.resize (dr + 1) ;
            rgt.resize (st + 1) ;
            viz.resize (st + 1, false) ;
            for (auto &x : edges) {
                gr [x.first].push_back (x.second) ;
                assert (isBetween (1, x.first, st)) ; 
                assert (isBetween (1, x.second, dr)) ;
            }
        }
        vector < pair <int, int> > Solve () {
            return _MaximalMatchinAlgorithm () ;
        }

private :
        int lftNodes, rgtNodes ;
        vector < vector <int> > gr;
        vector <bool> viz ; 
        vector <int> lft ; 
        vector <int> rgt ; 
        bool isBetween (int a, int b, int c) {
            return b >= a and b <= c ; 
        }
        bool _Match (int node) {
            if (viz [node]) return false ;
            viz [node] = 1 ; 
            for (auto &x : gr [node]) {
                if (lft [x] == 0) {
                    lft [x] = node ; 
                    rgt [node] = x ; 
                    return true ;
                }
            }
            for (auto &x : gr [node]) {
                if (_Match(lft [x])) {
                    lft [x] = node ; 
                    rgt [node] = x ; 
                    return true ;
                }
            }
            return false ;
        }
        vector < pair <int, int> > _MaximalMatchinAlgorithm () {
            bool ok ;
            do {
                ok = false ; 
                fill (viz.begin(), viz.end(), false) ;
                for (int i = 1 ; i <= lftNodes ; ++ i) {
                    if (rgt [i] == 0) {
                        ok |= _Match (i) ; 
                    }
                }
            } while (ok) ;
            vector < pair <int, int> > solution ; 
            for (int i = 1 ; i <= lftNodes ; ++ i) {
                if (rgt [i]) {
                    solution.push_back ({i, rgt [i]}) ;
                }
            }
            return solution ; 
        }
};

int readInt () {
        bool minus = false;
        int result = 0;
        char ch;
        ch = getchar();
        while (true) {
            if (ch == '-') break;
            if (ch >= '0' && ch <= '9') break;
                ch = getchar();
        }
        if (ch == '-') minus = true; else result = ch-'0';
        while (true) {
            ch = getchar();
            if (ch < '0' || ch > '9') break;
                result = result*10 + (ch - '0');
        }
        if (minus)
            return -result;
        else
            return result;
}

void write (int nr) {
    if (nr) write (nr / 10) ;
    else return  ;
    putchar ('0' + nr % 10) ;
}

int main () {
    freopen ("cuplaj.in", "r", stdin) ;
    freopen ("cuplaj.out", "w", stdout) ;
    int st, dr, m ; 
    st = readInt () ; 
    dr = readInt () ;
    m  = readInt () ;
    vector < pair <int, int> > edg ;
    while (m --) {
        int x, y ; 
        x = readInt () ;
        y = readInt () ; 
        edg.push_back ({x, y}) ;
    }
    MaximalMatching *Solve = new MaximalMatching (edg, st, dr) ;
    auto solution = Solve -> Solve () ;
    printf ("%d\n", (int) solution.size()) ; 
    for (auto &x : solution) {
        write (x.first); printf (" "); write (x.second); printf ("\n") ;
    }
    return 0 ; 
}