Cod sursa(job #302487)

Utilizator SleepyOverlordPatcas Csaba SleepyOverlord Data 8 aprilie 2009 22:24:23
Problema Flux maxim Scor 40
Compilator cpp Status done
Runda Arhiva educationala Marime 1.82 kb
//Code by Patcas Csaba
//Time complexity: O(n*m^2)
//Space complexity: O(m+n)
//Method: Edmonds-Karp, retin reteaua reziduala
//Working time: 30 minutes

#include <stdio.h>
#include <vector>
#include <queue>

using namespace std;

#define in_file "maxflow.in"
#define out_file "maxflow.out"

#define VI vector <int>

#define FORN(i,n) for (int i=0;i<n;++i)
#define FOR(i,a,b) for (int i=a;i<=b;++i)
#define ALL(x) x.begin(), x.end()
#define PB push_back
#define S size()

#define inf 111111


int n,m,solution;
vector <VI> c, g;
VI father, ind;

void bf()
{
	queue <int> l;
	l.push(1);
	while (!father[n] && !l.empty())
	{
		int node=l.front();
		FORN(i,g[node].S)
		{
			int aux=g[node][i];
			if (!father[aux] && c[node][aux])
			{
				father[aux]=node;
				ind[aux]=i;
				l.push(aux);
			}
		}
		l.pop();
	}
}

int IncreaseFlow()
{
	int node=n, flow=inf;
	while (node!=1)
	{
		flow=min(flow,c[father[node]][node]);
		node=abs(father[node]);
	}
	node=n;
	while (node!=1)
	{
		c[father[node]][node]-=flow;
		c[node][father[node]]+=flow;
		node=abs(father[node]);
	}
	return flow;
}

void EdmondsKarp()
{
	father.resize(n+1);
	ind.resize(n+1);
	solution=0;
	while (1) 
	{
		fill(ALL(father),0);
		bf();
		if (father[n]) 
		{
			int aux=IncreaseFlow();
			solution+=aux;
		}
		else break;
	}
}

void AddEdge(int node1, int node2, int cc)
{
	g[node1].PB(node2);
	g[node2].PB(node1);
	c[node1][node2]=cc;
	c[node2][node1]=0;
}

int main()
{
	FILE* fin=fopen(in_file,"r");
	fscanf(fin,"%d%d",&n,&m);
	g.resize(n+1);
	c.resize(n+1,VI(n+1,-1));
	FORN(q,m)
	{
		int x,y,z;
		fscanf(fin,"%d%d%d",&x,&y,&z);
		AddEdge(x,y,z);
	}
	fclose(fin);

	EdmondsKarp();

	FILE* fout=fopen(out_file,"w");
	fprintf(fout,"%d",solution);
	fclose(fout);

	return 0;
}