Cod sursa(job #1605674)

Utilizator algebristulFilip Berila algebristul Data 19 februarie 2016 13:03:26
Problema Critice Scor 100
Compilator cpp Status done
Runda contest_6 Marime 2.97 kb
#include <cstdio>
#include <cstring>
#include <vector>
#include <queue>

using namespace std;

const int INF  = 0x3f3f3f3f;
const int nmax = 1005;
const int mmax = 10005;

int n, m;
int OK[2][nmax];
vector<int> A[nmax];
int C[nmax][nmax];
int F[nmax][nmax];
int D[nmax];
int M[nmax];
int InQ[nmax];
pair<int, int> E[mmax];

bool bf_flux(int src, int dst) {
    memset(D, 0, sizeof(D));
    memset(InQ, 0, sizeof(InQ));
    memset(M, 0, sizeof(M));
    queue<int> Q;
    //D[src] = 1;
    InQ[src] = 1;
    M[src] = 1;
    Q.push(src);

    while (!Q.empty()) {
        int x = Q.front();
        Q.pop();
        InQ[x] = 0;

        if (x == dst) {
            continue;
        }

        for (int i = 0; i < A[x].size(); i++) {
            int y = A[x][i];

            if (F[x][y] < C[x][y] && !M[y]) {
                D[y] = x;
                M[y] = 1;
                if (!InQ[y]) {
                    Q.push(y);
                    InQ[y] = 1;
                }
            }
        }
    }

    if (!M[dst])
        return false;

    for (int i = 0; i < A[dst].size(); i++) {
        int x = A[dst][i];
        if (F[x][dst] >= C[x][dst] || !M[x])
            continue;
        D[dst] = x;

        int f = INF;
        int tmp = dst;
        while (tmp != src) {
            f = min(f, C[D[tmp]][tmp] - F[D[tmp]][tmp]);
            tmp = D[tmp];
        }

        if (!f)
            continue;

        tmp = dst;
        while (tmp != src) {
            F[D[tmp]][tmp] += f;
            F[tmp][D[tmp]] -= f;
            tmp = D[tmp];
        }
    }

    return true;
}

void flux() {
    while (bf_flux(1, n));
}

void bf(int s, int *v) {
    queue<int> Q;
    v[s] = 1;
    Q.push(s);

    while (!Q.empty()) {
        int x = Q.front();
        Q.pop();
        for (int i = 0; i < A[x].size(); i++) {
            int y = A[x][i];
            int flux = F[x][y] < 0 ? F[y][x] : F[x][y];
            if (flux < C[x][y] && !v[y]) {
                v[y] = 1;
                Q.push(y);
            }
        }
    }
}

int main() {
    freopen("critice.in", "r", stdin);
    freopen("critice.out", "w", stdout);

    scanf("%d %d", &n, &m);
    for (int i = 1, x, y, z; i <= m; i++) {
        scanf("%d %d %d", &x, &y, &z);
        A[x].push_back(y);
        A[y].push_back(x);
        C[x][y] = z;
        C[y][x] = z;
        E[i] = make_pair(x, y);
    }

    flux();
    bf(1, OK[0]);
    bf(n, OK[1]);

    vector<int> Ans;
    for (int i = 1; i <= m; i++) {
        int x = E[i].first, y = E[i].second;
        int flux = F[x][y] < 0 ? F[y][x] : F[x][y];

        if (flux == C[x][y]) {
            if (OK[0][x] && OK[1][y])
                Ans.push_back(i);
            else if (OK[0][y] && OK[1][x])
                Ans.push_back(i);
        }
    }

    printf("%d\n", Ans.size());
    for (int i = 0; i < Ans.size(); i++)
        printf("%d\n", Ans[i]);

    return 0;
}