Cod sursa(job #2112079)

Utilizator silkMarin Dragos silk Data 22 ianuarie 2018 23:04:28
Problema Critice Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.23 kb
#include <bits/stdc++.h>
#define MaxN 1000
#define MaxM 10000
#define x first
#define y second
using namespace std;

pair<int, int> v[MaxM+1];
vector<int> L[MaxN+1];
int f[MaxN+1][MaxN+1];
int c[MaxN+1][MaxN+1];
int from[2][MaxN+1];
int sol[MaxM+1];
int t[MaxN+1];
int N,M,res;

void AddEdge(int x, int y, int cap)
{
    L[x].push_back(y);
    c[x][y] = cap;
}

int BFS()
{
    memset(t, 0, sizeof(t));
    queue<int> Q;

    Q.push(1);
    t[1] = 1;
    while(!Q.empty())
    {
        int x = Q.front();
        Q.pop();

        for(auto y : L[x])
        if(!t[y] && f[x][y] < c[x][y])
        {
            t[y] = x;
            Q.push(y);
        }
    }

    return t[N];
}

void MaxFlow()
{
    int i,qnt;

    while(BFS())
        for(auto x : L[N])
        {
            qnt = c[x][N] - f[x][N];
            for(i = x; i > 1; i = t[i]) qnt = min(qnt, c[ t[i] ][i] - f[ t[i] ][i]);
            if(!qnt) continue;

            f[x][N] += qnt;
            f[N][x] -= qnt;
            for(i = x; i > 1; i = t[i])
            {
                f[ t[i] ][i] += qnt;
                f[i][ t[i] ] -= qnt;
            }
        }
}

void Compute(int l, int S)
{
    queue<int> Q;

    Q.push(S);
    from[l][S] = 1;
    while(!Q.empty())
    {
        int x = Q.front();
        Q.pop();

        for(auto y : L[x])
        if(!from[l][y] && abs(f[x][y]) < max(c[x][y], c[y][x]))
        {
            from[l][y] = 1;
            Q.push(y);
        }
    }
}


int main(){
    FILE* fin = fopen("critice.in","r");
    FILE* fout = fopen("critice.out","w");

    int i,j,x,y,z;

    fscanf(fin,"%d %d",&N,&M);
    for(i = 1; i <= M; ++i)
    {
        fscanf(fin,"%d %d %d",&x,&y,&z);
        AddEdge(x,y,z);
        AddEdge(y,x,z);
        v[i] = {x, y};
    }

    MaxFlow();
    Compute(0, 1);
    Compute(1, N);
    for(i = 1; i <= M; ++i)
        if(f[ v[i].x ][ v[i].y ] < 0) swap(v[i].x, v[i].y);

    for(i = 1; i <= M; ++i)
    {
        x = v[i].x; y = v[i].y;
        if(from[0][x] && from[1][y] && f[x][y] == c[x][y]) ++res, sol[i] = 1;
    }

    fprintf(fout,"%d\n",res);
    for(i = 1; i <= M; ++i)
    if(sol[i]) fprintf(fout,"%d\n",i);


return 0;
}