Cod sursa(job #80904)

Utilizator vladcoderVlad Ion vladcoder Data 30 august 2007 15:23:44
Problema Cc Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.16 kb
#include <stdio.h>
#include <string.h>
#define FIN "cc.in"
#define FOUT "cc.out"
#define NMAX 205
#define ABS( a ) ( (a) < 0 ) ? - a : a 
#define infinit 1000000000

int C[NMAX][NMAX], FLOW[NMAX][NMAX], CAP[NMAX][NMAX];
int T[NMAX], SEL[NMAX], Q[NMAX*NMAX], D[NMAX];
int N, i, j, sursa, dest;
FILE * fin, * fout;

void RELAX( int nod )
{
	int tata;
	while (T[nod] != 0 )
	{
		tata = ABS( T[nod] );
		if (T[nod] > 0) FLOW[tata][nod]++;
		else FLOW[nod][tata]--;
		nod = tata;
	}
}

void Bellman_Ford()
{
 int p = 1, u = 1, nod;
 memset( SEL, 0, sizeof(SEL));
 memset( T, 0, sizeof(T) );
 for( i = sursa; i <= dest; i++ ) D[i] = infinit;
 D[sursa] = 0;  Q[1] = sursa; SEL[sursa] = 1; 
  while ( p <= u )
  {
	  nod = Q[p];
	  for( i = sursa; i <= dest; i++ )
		  if ( D[i] > D[nod] + C[nod][i] )
	  {
		  if ( CAP[nod][i] - FLOW[nod][i] > 0 )
		  {
			  T[i] = nod; D[i] = D[nod] + C[nod][i];
			  if (!SEL[i]) 
			  { 
				  u++; Q[u] = i; SEL[i] = 1;
			  }
		  }else
			  if( FLOW[i][nod] > 0 )
			  {
				  T[i] = - nod; D[i] = D[nod] + C[nod][i];
				  if(!SEL[i])
				  {
					  u++; Q[u] = i; SEL[i] = 1;
				  }
			  }
		  }
		  SEL[nod] = 0; p++;
  }
}



void DO_FLOW()
{
	do
	{
		Bellman_Ford();
		if (D[dest] != infinit ) RELAX(dest);
	}while( D[dest] != infinit);
}



int main()
{
	fin = fopen( FIN, "r" );
	fout = fopen( FOUT, "w" );
	fscanf( fin, "%d\n", &N );
	memset( CAP, 0, sizeof(CAP));
	memset( FLOW, 0, sizeof(FLOW));
	memset( C, 0, sizeof(C));

	for( i = 1; i <= N; i++)
		for( j = 1; j <= N; j++ ) 
		{
			fscanf( fin, "%d", &C[i+1][j+1+N] );
			C[j+1+N][i+1] = - C[i+1][j+1+N];
			CAP[i+1][j+1+N] = 1;
		}
     sursa = 1; dest = 2 * N + 2;
	 for( i = 2; i <= N + 1; i++)
	 {
		 C[sursa][i] = 1; C[i][sursa] = - 1;
		 CAP[sursa][i] = 1;
	 }
	 for( i = N + 2; i < dest; i++) 
	 {
		 CAP[i][dest] = 1;
		 C[i][dest] = 1; C[dest][i] = - 1;
	 }
     DO_FLOW();
	 int cost = 0;
	 for( i = 2; i <= N + 1; i++)
		 for( j = N + 2; j < dest; j++)
			 if( FLOW[i][j]) cost += C[i][j];
				 
     fprintf( fout, "%d\n", cost );
	 fclose( fin );
	 fclose( fout );
	 return 0;
}