Cod sursa(job #1865699)

Utilizator FlorinHajaFlorin Gabriel Haja FlorinHaja Data 1 februarie 2017 23:12:41
Problema Flux maxim de cost minim Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 2.91 kb
#include <fstream>
#include <set>
#include <vector>
#include <utility>
#include <vector>
#include <algorithm>
#include <cstring>
#define maxn 355
#define maxx 1000010

using namespace std;

vector <int> ls[maxn];
int cap[maxn][maxn], f[maxn][maxn], cs[maxn][maxn], dist[maxn], distT[maxn], distV[maxn], FMIN;
long long sol;
const int f_mare = 2e9;
int n, m, inc, sf, x, y, z, t, tt[maxn], g[maxn], i;
bool viz[maxn], ok;
int coada[maxx], st, dr;
set<pair<int,int> >cd;


int dijkstra() {
    int i, j;
    for (i = 1; i <= n; i++) {
        dist[i] = distT[i] =f_mare;
        tt[i] = -1;
    }
    cd.clear();
    dist[inc]=distT[inc] = 0;
    cd.insert(make_pair(0, inc));

    while (cd.empty() == 0) {
        x = cd.begin() -> second;
        cd.erase(cd.begin());
        for (i = 0; i < g[x]; i++) {
            y = ls[x][i];
            if (cap[x][y]-f[x][y] > 0 && (j=distT[x] + cs[x][y] + distV[x]-distV[y]) < distT[y]) {
                if (dist[y] != f_mare)
                    cd.erase(cd.find(make_pair(distT[y], y)));
                dist[y] = dist[x] + cs[x][y];
                tt[y]=x;
                cd.insert(make_pair((distT[y]=j), y));
            }
        }
    }
    memcpy(distV, dist, sizeof(dist));

    if (dist[sf] != f_mare) {
        ok = 1;
        FMIN = f_mare;
        y = sf;
        while (y != inc) {
            FMIN = std::min(FMIN, cap[tt[y]][y]-f[tt[y]][y]);
            y = tt[y];
        }

        y = sf;
        while (y != inc) {
            f[tt[y]][y] += FMIN;
            f[y][tt[y]] -= FMIN;
            y = tt[y];
        }
        return distV[sf]*FMIN;
    }

    return 0;
}

int bf() {
    int i;
    for (i = 1; i <= n; i++) {
        distV[i] = f_mare;
        viz[i] = 0;
    }
    distV[inc] = 0;
    viz[inc] = 1;
    coada[(st = dr = 0)] = inc;
    while (st <= dr) {
        x = coada[st++];
        viz[x] = 0;
        for (i = 0; i < g[x]; i++) {
            y = ls[x][i];
            if (cap[x][y]) {
                if (distV[x] + cs[x][y] >= distV[y])
                    continue;
                distV[y] = distV[x] + cs[x][y];
                if (viz[y] == 1)
                    continue;
                viz[y] = 1;
                coada[++dr] = y;
            }
        }
    }
    return distV[sf] != f_mare;
}

void calc() {

    ok=1;
    while (ok) {
        ok = 0;
        sol += dijkstra();
    }

}

int main() {
    ifstream in("fmcm.in");
    ofstream out("fmcm.out");
    in>>n>>m>>inc>>sf;
    while (m--) {
        in>>x>>y>>z>>t;
        //fscanf(F, "%d %d %d %d\n", &x, &y, &z, &t);
        ls[x].push_back(y);
        ls[y].push_back(x);
        cap[x][y] = z;
        cs[x][y] = t;
        cs[y][x] = -t;
    }
    for (i = 1; i <= n; i++)
        g[i] = ls[i].size();
    bf();
    calc();

    //fprintf(G,"%d",sol);
    out << sol;
    return 0;
}