Cod sursa(job #254906)

Utilizator stocarulCosmin-Mihai Tutunaru stocarul Data 8 februarie 2009 01:30:43
Problema Flux maxim Scor 20
Compilator c Status done
Runda Arhiva educationala Marime 2.2 kb
#include<stdio.h>
#define infile "maxflow.in"
#define outfile "maxflow.out"
#define nmax 1001
#define mmax 5001
#define inf ~(1<<31)
struct lista
	{
	int n,p; //nodul...si pozitia lu frasu
	int f,c; //fluxul folosit, si capacitatea totala a arcului
	} l[mmax];
struct nod
	{
	int p; //pozitia din lista
	char v; //v=1 daca prin intermediul acestui nod nu mai putem mari fluxul
	} n[nmax];
int s=1,d; //nodul sursa (primul nod) si numarul de noduri(ultimul fiind si nodul destinatie)
int flux; //aici vom calcula fluxul maxim intregii retele ;))

int minim(int a, int b)
	{
	if(a<b) return a;
	return b;
	}

//adaugam arcul in lsita....
void add(struct lista l[mmax], struct nod n[nmax], int m, int x, int y, int c)
	{
	l[m].n=y; l[m].c=c; l[m].p=n[x].p; n[x].p=m;
	}

void citire(struct lista l[mmax], struct nod n[nmax], int *d)
	{
	int i,m,x,y,z;
	scanf("%d %d\n",d,&m);
	for(i=1;i<=m;i++)
		{
		scanf("%d %d %d\n",&x,&y,&z);
		add(l,n,i,x,y,z); //adaugam arcul (x,y) cu costul c in lista
		}
	}

//va folosi structurile lista si nod globale...la fel si variabilele d si flux
int dfs(int x, int c) //se ajunge la nodul x cu costul c
	{
	if(x==d) { flux+=c; return 0; } //daca e nodul de destinatie...salvez costul..si returnez 0 :>
	int y,z,f,ul=n[x].p; //pozitia din lista a unui copil
	while(ul&&c) //cat timp are copii, si mai avem cost (adica flux)
		{
		y=l[ul].n; //copilul lui x
		if(!n[y].v) //daca il putem parcurge, adica ne poate imbunatatii fluxul
			{
			f=minim(c,l[ul].c-l[ul].f); //fluxul maxim cu care paote fi apelat acest nod
			if(f) //daca se paote apela ;))
				{
				z=dfs(y,f); //parcurgem acest nod (cu minimum dintre cat avem si cat poate ;)))...si primim flux...daca nu foloseste tot
				if(z&&y!=d) n[y].v=1; //nu ne mai ducem alta data la acest nod ;))
				l[ul].f+=(f-z); //salvam fluxul care s-a folosit
				c=c-f+z; //repunem in z cat a mai ramas
				}
			}
		ul=l[ul].p; //frasu
		}
	return c;
	}

int main()
{
freopen(infile,"r",stdin);
freopen(outfile,"w",stdout);

citire(l,n,&d); //citim datele din fisier
dfs(1,inf); //parcurgem pt nodul 1...cu flux infinit
printf("%d",flux); //afisem fluxul

fclose(stdin);
fclose(stdout);
return 0;
}