Cod sursa(job #1106870)

Utilizator alexalghisiAlghisi Alessandro Paolo alexalghisi Data 13 februarie 2014 12:05:50
Problema Critice Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.06 kb
#include <iostream>
#include <fstream>
#include <cstdio>
#include <vector>
#include <bitset>
#include <cmath>
#include <queue>
#include <string>
#include <map>
#include <set>


#define DN 1005
#define pb push_back
#define mp make_pair
#define per pair<int,int>
#define INF (1<<30)
#define un unsigned
#define x first
#define y second
using namespace std;

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

int C[DN][DN],F[DN][DN],n,m,t[DN],arb[DN];
vector<int> list[DN],rez;
vector< per > v;
queue<int> q;
bitset<DN> viz,first,last;


void bfa(int nod)
{
    q.push(nod);
    viz&=0;
    while(q.size())
    {
        int nod = q.front();
        first[ nod ] = true;
        q.pop();
        for(un int i=0;i<list[nod].size();++i){

            int next_nod = list[nod][i];
            if(!viz[nod] && !first[next_nod] && C[nod][next_nod] != abs(F[nod][next_nod]) )
                q.push(next_nod);
        }
    }
}

void bfb(int nod)
{
    q.push(nod);
    viz&=0;
    while(q.size())
    {
        int nod = q.front();
        last[ nod ] = true;
        q.pop();
        for(un int i=0;i<list[nod].size();++i){

            int next_nod = list[nod][i];
            if(!viz[nod] && !last[next_nod] && C[nod][next_nod] != abs(F[nod][next_nod]) )
                q.push(next_nod);
        }
    }
}


bool bf() /// construim arborele bfs
{
    viz&=0;
    arb[0]=1;
    arb[1]=1;

    viz[1]=1;
    for(int i=1;i<=arb[0];++i)
    {
        int nod = arb[i];
        if(nod == n)
            return viz[n];
        for(un int j=0;j<list[nod].size();++j){

            int next_nod = list[nod][j];
            if( C[nod][next_nod] == F[nod][next_nod] || viz[next_nod] ) continue;
            viz[next_nod] = true;
            arb[ ++arb[0] ] = next_nod;
            t[next_nod] = nod;
        }
    }
    return viz[n];
}



void solve()
{
    bool exista_flux = true;
    for( ; exista_flux ; )
    {
        exista_flux = bf();
        for(un int i=0;i<list[n].size();++i)
        {
            int nod = list[n][i] , fmin = INF;
            if( C[ nod ][ n ] == F[ nod ][ n ] || !viz[nod] ) continue;
            t[ n ] = nod;

            for( nod = n ; nod!=1 ; nod=t[nod])
                fmin = min(fmin, C[ t[nod] ][ nod ] - F[ t[nod] ][ nod ] );

            if(fmin == 0) continue;

            for( nod = n ; nod!=1 ; nod=t[nod]){

                F[ t[nod] ][ nod ] +=fmin;
                F[ nod ][ t[nod] ]-=fmin;
            }
        }
    }

    bfa(1);
    bfb(n);
    for(un int i=0;i<v.size();++i)
    {
        int a = v[i].x;
        int b = v[i].y;
        if(  (( first[a]&last[b] ) && C[a][b]==F[a][b] )
                    || ( ( first[b]&last[a]  ) && C[b][a]==F[b][a]) )
                rez.pb(i+1);
    }
}

void write()
{
    g<<rez.size()<<"\n";
    for(un int i=0;i<rez.size();++i)
        g<<rez[i]<<"\n";
}

void read()
{
    f>>n>>m;
    for(int i=1;i<=m;++i)
    {
        int a,b,c;
        f>>a>>b>>c;
        v.pb(mp(a,b));

        C[a][b]+=c;
        C[b][a]+=c;
        list[a].pb(b);
        list[b].pb(a);
    }
}

int main()
{
    read();
    solve();
    write();

    return 0;
}