Cod sursa(job #572713)

Utilizator katakunaCazacu Alexandru katakuna Data 5 aprilie 2011 16:04:46
Problema Flux maxim de cost minim Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.92 kb
#include <cstdio>
#include <algorithm>
#include <string.h>
#include <vector>
#include <queue>
using namespace std;

#define Nmax 355
#define INF 0x3f3f3f3f

int n, m, S, D;
int Dist[Nmax];
short int F[Nmax][Nmax], C[Nmax][Nmax], T[Nmax];
bool viz[Nmax];
queue <short int> Q;
vector < pair <short int, short int> > V[Nmax];

void citire () {

    int i, x, y, c, z;

    scanf ("%d %d %d %d", &n, &m, &S, &D);
    for (i = 1; i <= m; i++) {
        scanf ("%d %d %d %d", &x, &y, &c, &z);
        V[x].push_back ( make_pair (y, z) );
        V[y].push_back ( make_pair (x, -z) );
        C[x][y] = c;
    }
}

bool bellman_ford () {

    memset (Dist, INF, sizeof (Dist));
    memset (viz, 0, sizeof (viz));

    int nod;
    vector < pair <short int, short int> >::iterator it;

    for (Q.push (S), viz[S] = 1, Dist[S] = 0; !Q.empty (); Q.pop ()) {
        nod = Q.front (); viz[nod] = 0;
        for (it = V[nod].begin (); it != V[nod].end (); it++)

            if (C[nod][it->first] > F[nod][it->first] && Dist[it->first] > Dist[nod] + it->second) {
                Dist[it->first] = Dist[nod] + it->second;
                T[it->first] = nod;
                if (!viz[it->first]) {
                    viz[it->first] = 1;
                    Q.push (it->first);
                }
            }
    }

    if (Dist[D] != INF) return 1;
    return 0;
}

void fmcm () {

    int cost = 0, nod, minim;
    while ( bellman_ford () ) {

        minim = C[T[D]][D] - F[T[D]][D];
        for (nod = D; T[nod]; nod = T[nod])
            if (minim > C[T[nod]][nod] - F[T[nod]][nod])
                minim = C[T[nod]][nod] - F[T[nod]][nod];

        for (nod = D; T[nod]; nod = T[nod]) {
            F[T[nod]][nod]+= minim;
            F[nod][T[nod]]-= minim;
        }

        cost+= minim * Dist[D];
    }

    printf ("%d\n", cost);
}

int main () {

    freopen ("fmcm.in", "r", stdin);
    freopen ("fmcm.out", "w", stdout);

    citire ();
    fmcm ();

    return 0;
}