Cod sursa(job #1065992)

Utilizator florin.elfusFlorin Elfus florin.elfus Data 23 decembrie 2013 21:35:29
Problema Flux Scor 88
Compilator cpp Status done
Runda Lista lui wefgef Marime 2.62 kb
#include <stdio.h>
#include <assert.h>

const double EPS = 1e-12;

bool adj[111][111];
int cmin[111][111];
double res[111], M[111][111];

void add(int xx, int yy, int cc) {
    adj[xx][yy] = 1;
    if (cc < cmin[xx][yy])
        cmin[xx][yy] = cc;
    if (xx != 1) {
        ++M[xx][xx];
        --M[xx][yy];
    }
}

void swap(double &A, double &B) {
    double tmp = A;
    A = B;
    B = tmp;
}

double abs(double X) {
    return X > 0 ? X : -X;
}

bool mlc;

void eliminareGaozara(int N, int m) {
    int i = 1, j = 1, k;
    while (i <= N && j <= m) {
        for (k = i; k <= N; ++k)
            if (abs(M[k][j]) > EPS)
                break;
        if (k == N + 1) {
            ++j;
            continue;
        }
        for (int c = 1; c <= m + 1; ++c)
            swap(M[i][c], M[k][c]);
        double ret = M[i][j];
        for (k = 1; k <= m + 1; ++k)
            M[i][k] /= ret;
        for (k = i + 1; k <= N; ++k) {
            ret = M[k][j];
            for (int c = 1; c <= m + 1; ++c)
                M[k][c] = -M[k][c] + ret * M[i][c];
        }
        ++i; ++j;
    }

    for (i = N; i >= 1; --i) {
        for (j = 1; j <= m + 1; ++j)
            if (!(abs(M[i][j]) <= EPS)) {
                if (j == m + 1)
                    mlc = 1;
                else {
                    res[i] = M[i][m + 1];
                    for (int pula = m; pula > j; --pula)
                        res[i] -= res[pula] * M[i][pula];
                    res[i] = res[i] / M[i][j];
                }
                break;
            }
    }
}

int vis[115];

void dfs(int nod) {
    vis[nod] = 1;
    for (int i = 1; i <= 100; ++i)
        if (!vis[i] && adj[nod][i])
            dfs(i);
}

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

    int N, m;
    scanf("%d%d", &N, &m);
    for (int i = 1; i <= N; ++i)
        for (int j = 1; j <= N; ++j)
            cmin[i][j] = 1000000000.0;
    for (int i = 1; i <= m; ++i) {
        int xx, yy, cc;
        scanf("%d%d%d", &xx, &yy, &cc);
        add(xx, yy, cc);
        add(yy, xx, cc);
    }
    M[1][1] = 1;
    M[N][N + 1] = 1;

    eliminareGaozara(N, N);

    double scalar = -69;
    for (int i = 1; i <= N; ++i)
        for (int j = 1; j <= N; ++j)
            if (adj[i][j])
                if (scalar - abs((double)cmin[i][j] / (res[j] - res[i])) > EPS || scalar == -69)
                    scalar = abs((double)cmin[i][j] / (res[j] - res[i]));
    double sol = 0;
    dfs(1);
    if (vis[N])
        sol = scalar;
    printf("%.3lf", sol);
    return 0;
}