Cod sursa(job #1669222)

Utilizator tudormaximTudor Maxim tudormaxim Data 30 martie 2016 15:36:32
Problema Flux maxim de cost minim Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.77 kb
#include <iostream>
#include <fstream>
#include <vector>
#include <queue>
#include <bitset>
using namespace std;

ifstream fin ("fmcm.in");
ofstream fout ("fmcm.out");

const int nmax = 355;
const int oo = 1e9;
vector <int> g[nmax];
bitset <nmax> viz;
int source, dest, n, m;
int cost[nmax][nmax], cap[nmax][nmax], flow[nmax][nmax];
int real_d[nmax], old_d[nmax], d[nmax], dady[nmax];

void bellman() {
    vector <int> :: iterator son;
    queue <int> q;
    int dad, i;
    for(i=1; i<=n; i++) {
        old_d[i]=oo;
    }
    old_d[source]=0;
    viz[source]=true;
    q.push(source);
    while(!q.empty()) {
        dad=q.front();
        viz[dad]=false;
        q.pop();
        for(son=g[dad].begin();son!=g[dad].end(); son++)
            if(cap[dad][*son] && old_d[*son] > old_d[dad]+cost[dad][*son]) {
                old_d[*son]=old_d[dad]+cost[dad][*son];
                if(!viz[*son] && *son!=dest) {
                    viz[*son]=true;
                    q.push(*son);
                }
            }
    }
}

int dijkstra() {
    priority_queue<pair<int,int>, vector<pair<int,int> >, greater<pair<int,int> > > heap;
    vector <int> :: iterator son;
    int dad, cst, i, new_dist;
    for(i=1; i<=n; i++) {
        d[i]=real_d[i]=oo;
    }
    d[source]=real_d[source]=0;
    heap.push({0, source});
    while(!heap.empty()) {
        dad=heap.top().second;
        cst=heap.top().first;
        heap.pop();
        if(d[dad]!=cst) continue;
        for(son=g[dad].begin(); son!=g[dad].end(); son++)
            if(cap[dad][*son] > flow[dad][*son]) {
                new_dist=d[dad]+cost[dad][*son]+old_d[dad]-old_d[*son];
                if(d[*son] > new_dist) {
                    d[*son]=new_dist;
                    real_d[*son]=real_d[dad]+cost[dad][*son];
                    dady[*son]=dad;
                    if(*son!=dest) heap.push({d[*son], *son});
                }
            }
    }
    for(i=1; i<=n; i++) {
        old_d[i]=real_d[i];
    }
    return d[dest]!=oo;
}

int main() {
    ios_base::sync_with_stdio(false);
    int i, x, y, a, c, max_flux=0, flux;
    fin >> n >> m >> source >> dest;
    for(i=1; i<=m; i++)
    {
        fin >> x >> y >> a >> c;
        g[x].push_back(y);
        g[y].push_back(x);
        cap[x][y]=a;
        cost[x][y]=c;
        cost[y][x]=-c;
    }
    bellman();
    while(dijkstra()) {
        flux=oo;
        for(i=dest; i!=source; i=dady[i]) {
            flux=min(flux, cap[dady[i]][i]-flow[dady[i]][i]);
        }
        for(i=dest; i!=source; i=dady[i]) {
            flow[dady[i]][i]+=flux;
            flow[i][dady[i]]-=flux;
        }
        max_flux+=flux*old_d[dest];
    }
    fout << max_flux;
    fin.close();
    fout.close();
    return 0;
}