Cod sursa(job #1212090)

Utilizator mariusn01Marius Nicoli mariusn01 Data 23 iulie 2014 19:45:59
Problema Cuplaj maxim de cost minim Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.04 kb
#include <fstream>
#include <vector>
#include <queue>
#include <bitset>
#include <cstring>

#define DIM 610
#define INF 100000000

using namespace std;
ifstream fin("cmcm.in");
ofstream fout("cmcm.out");

vector <pair<int, int> > L[DIM];
queue<int> Q;
bitset<DIM> inQueue;
int T[DIM], D[DIM];
int C[DIM][DIM], F[DIM][DIM], Z[DIM][DIM];

int n, m, e, x, i, j, cost, cuplaj, c, y;

int bellmanFord() {
    int ok = 0, x, y;
    for (int i=0;i<=n+m+1;i++)
        D[i] = INF;
    memset(T, 0, sizeof(T));
    D[0] = 0;
    Q.push(0);
    inQueue[0] = 1;
    while (!Q.empty()) {
        x = Q.front();
        Q.pop();
        inQueue[x] = 0;

        for (int i=0; i<L[x].size(); i++) {
            y = L[x][i].first;
            if (C[x][y] > F[x][y] && D[y] > D[x] + Z[x][y]) {
                D[y] = D[x] + Z[x][y];
                T[y] = x;
                if (y == n+m+1)
                    ok = 1;
                if (!inQueue[y])
                    Q.push(y);
            }
        }

    }
    return ok;
}

int main() {
    fin>>n>>m>>e;
    for (i=1;i<=e;i++) {
        fin>>x>>y>>c;
        L[x].push_back(make_pair(y+n, i));
        L[y+n].push_back(make_pair(x, i));
        C[x][y+n] = 1;
        Z[x][y+n] = c;
        Z[y+n][x] = -c;
    }

    for (i=1;i<=n;i++) {
        L[0].push_back(make_pair(i, 0));
        L[i].push_back(make_pair(0, 0));
        C[0][i] = 1;
    }

    for (i=n+1;i<=n+m;i++) {
        L[i].push_back(make_pair(n+m+1, 0));
        L[n+m+1].push_back(make_pair(i, 0));
        C[i][n+m+1] = 1;
    }
    while (bellmanFord()) {
        cuplaj++;
        x = n+m+1;
        do {
            y = T[x];
            F[y][x] ++;
            F[x][y] --;
            x = y;
        } while (y!=0);
        cost += D[n+m+1];
    }

    fout<<cuplaj<<" "<<cost<<"\n";
    for (i=1;i<=n;i++) {
        for (j=0;j<L[i].size();j++)
            if( F[i][ L[i][j].first ] == 1) {
                fout<<L[i][j].second<<" ";
            }
    }



    return 0;
}