Cod sursa(job #38788)

Utilizator sima_cotizoSima Cotizo sima_cotizo Data 26 martie 2007 09:55:38
Problema Drumuri minime Scor 25
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.56 kb
#include <cstdio>
#include <cstring>
#include <cmath>
#define FIN "dmin.in"
#define FOUT "dmin.out"
#define MAX 1501
#define inf 0x3f3f3f
#define eps 0.00001

double C[MAX][MAX];
double D[MAX];
long Nr[MAX]; 
bool used[MAX];
long n, m;

void debug(double d[]) {
	long i;
	for (i=1; i<=n; ++i)
		printf("%.3lf %ld\n", d[i], (long) exp(d[i]));
}

inline double abs(double x) {
	if ( x<0 ) 
		return -x;
	else 
		return x;
}

void dij() {
	long i;
	for (i=0; i<=n; ++i) 
		D[i] = inf;
	
	D[1] = 0;
//	Nr[1] = 1;
	while ( 1 ){
		long min = 0;
		for (i=1; i<=n; ++i)
			if ( D[i]<D[min] && !used[i] )
				min = i;
		if ( !min ) 
			break;
		used[min] =  true;
		for (i=1; i<=n; ++i) 
			if ( i!=min ) {
				if ( D[i] > D[min]+C[min][i] ) 
					D[i] = D[min] + C[min][i];
			}
	}
}

void bf(long x) {
	long i,j;
	long Q[MAX], p, u;
	used[x] = true;
	for ( Q[p=u=0]=x; p<=u; ++p) {
		i = Q[p];
		for (j=1; j<=n; ++j)
			if ( abs( D[i]+C[i][j]-D[j] ) < eps && i-j) {
				if ( !used[j] ) {
					Q[++u] = j;
                         used[j] = true;
                    }
				Nr[j] += Nr[i];
			}
	}
}

void init() {
	long i,j;
	for (i=1; i<=n; ++i)
		for (j=1; j<=n; ++j)
			if ( i-j ) 
				C[i][j] = inf;
}

int main() {
	long i;
	freopen(FIN, "r", stdin);
	scanf("%ld %ld", &n, &m);
	init();
	for (i=0; i<m; ++i) {
		long x,y,z;
		scanf("%ld %ld %ld", &x, &y, &z);
		C[x][y] = log((double)z);
	}
	fclose(stdin);
	
	dij();
	Nr[1] = 1;
	memset(used, false, sizeof(used));
	bf(1);

	freopen(FOUT, "w", stdout);
	for (i=2; i<n; ++i)
		printf("%ld ", Nr[i]);
	printf("%ld\n", Nr[i]);
	fclose(stdout);
	return 0;
}