Cod sursa(job #1491543)

Utilizator geniucosOncescu Costin geniucos Data 25 septembrie 2015 17:17:40
Problema Flux Scor 100
Compilator cpp Status done
Runda Lista lui wefgef Marime 2.36 kb
#include<cstdio>

using namespace std;

int N, M, N_init, M_init, a[5009], b[5009], c[5009], ap[109][109], cnt[109], fixed[109], Ap[109], t[109], cod[109], a_init[5009], b_init[5009], c_init[5009];
double mini, G[109][109], X[109], eps;

double mod (double x)
{
    if (x < 0.0) return -x;
    return x;
}

int tata (int x)
{
    if (x == t[x]) return x;
    return t[x] = tata (t[x]);
}

void unite (int x, int y)
{
    x = tata (x), y = tata (y);
    if (x != y) t[x] = y;
}

int main ()
{
freopen ("flux.in", "r", stdin);
freopen ("flux.out", "w", stdout);

scanf ("%d %d", &N_init, &M_init), eps = 1e-11;
for (int i=1; i<=N_init; i++)
    t[i] = i;

for (int i=1; i<=M_init; i++)
    scanf ("%d %d %d", &a_init[i], &b_init[i], &c_init[i]), unite (a_init[i], b_init[i]);

for (int i=1; i<=N_init; i++)
    if (tata (i) == tata (1))
        cod[i] = ++N;

if (tata (1) != tata (N_init))
{
    printf ("0.000\n");
    return 0;
}

for (int i=1; i<=M_init; i++)
    if (cod[a_init[i]] && cod[b_init[i]])
        a[++M] = cod[a_init[i]], b[M] = cod[b_init[i]], c[M] = c_init[i];

for (int i=1; i<=M; i++)
    cnt[a[i]] ++, cnt[b[i]] ++, ap[a[i]][b[i]] ++, ap[b[i]][a[i]] ++;

for (int i=1; i<=N; i++)
{
    if (i == 1) G[i][1] = 1.0, G[i][N + 1] = 0.0;
    else
    {
        G[i][i] = cnt[i];
        for (int j=1; j<=N; j++)
            if (i != j) G[i][j] = (double)-ap[i][j];
        G[i][N + 1] = 0.0;
        if (i == N) G[i][N + 1] = 1.0;
    }
}

for (int i=1; i<=N; i++)
{
    int j;
    for (j=1; j<=N + 1; j++)
        if (mod (G[i][j]) > eps) break;
    if (j == N + 1)
    {
        printf ("0.000\n");
        return 0;
    }
    if (j > N) continue;
    fixed[i] = j, Ap[j] = 1;
    for (int p=1; p<=N; p++)
        if (p != i && mod (G[p][j]) > eps)
        {
            double r = (double) G[p][j] / G[i][j];
            for (int k=1; k<=N + 1; k++)
                G[p][k] = (double) G[p][k] - G[i][k] * r;
        }
}

for (int i=1; i<=N; i++)
    if (Ap[i] == 0)
    {
        printf ("0.000\n");
        return 0;
    }

for (int i=1; i<=N; i++)
    X[fixed[i]] = (double) G[i][N + 1] / G[i][fixed[i]];

for (int i=1; i<=M; i++)
{
    double C = mod (X[b[i]] - X[a[i]]);
    if ((double) c[i] / C < mini || i == 1)
        mini = (double) c[i] / C;
}
printf ("%.10lf\n", mini);

return 0;
}