Cod sursa(job #1207242)

Utilizator iordache.bogdanIordache Ioan-Bogdan iordache.bogdan Data 12 iulie 2014 16:54:37
Problema Cuplaj maxim de cost minim Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.12 kb
#include <fstream>
#include <vector>
#include <queue>
#define DIMN 650
#define DIMM 50001
#define INF 2000000000

using namespace std;

ifstream f("cmcm.in");
ofstream g("cmcm.out");

pair<int,int> muchii[DIMM];

int F[DIMN][DIMN], C[DIMN][DIMN], cost[DIMN][DIMN], D[DIMN], T[DIMN];

bool viz[DIMN];

bool ok;

int n, m, n1, n2, k, flow, x, y, c;

vector<int> L[DIMN];

int BF () {
    queue<int> q;
    for (int i=0; i<=n; ++i)
        viz[i] = 0, D[i] = INF;
    q.push(0);
    D[0] = 0;
    while (!q.empty()) {
        int nod = q.front();
        q.pop();
        viz[nod] = 0;
        for (vector<int>::iterator it=L[nod].begin(); it!=L[nod].end(); ++it)
            if (D[*it] > D[nod] + cost[nod][*it] && C[nod][*it] - F[nod][*it] > 0) {
                D[*it] = D[nod] + cost[nod][*it];
                if (!viz[*it]) {
                    viz[*it] = 1;
                    q.push(*it);
                }
                T[*it] = nod;
            }
    }
    if (D[n] != INF) {
        ok = true;
        int Min = INF;
        for (int i=n; i!=0; i=T[i])
            Min = min(Min, C[T[i]][i] - F[T[i]][i]);
        flow += Min;
        for (int i=n; i!=0; i=T[i]) {
            F[T[i]][i] += Min;
            F[i][T[i]] -= Min;
        }
        return Min*D[n];
    }
    return 0;
}

int main () {
    f >> n1 >> n2 >> m;
    for (int i=1; i<=m; ++i) {
        f >> x >> y >> c;
        y += n1;
        L[x].push_back(y);
        L[y].push_back(x);
        muchii[++k] = make_pair(x,y);
        C[x][y] = 1;
        cost[x][y] = c;
        cost[y][x] = -c;
    }
    for (int i=1; i<=n1; ++i) {
        L[0].push_back(i);
        L[i].push_back(0);
        C[0][i] = 1;
    }
    n = n1+n2+1;
    for (int i=n1+1; i<n; ++i) {
        L[n].push_back(i);
        L[i].push_back(n);
        C[i][n] = 1;
    }
    ok = true;
    int ans = 0;
    while (ok) {
        ok = false;
        ans += BF();
    }
    g << flow << " " << ans << "\n";
    for (int i=1; i<=m; ++i)
        if (F[muchii[i].first][muchii[i].second] != 0)
            g << i << " ";
    return 0;
}