Cod sursa(job #1601366)

Utilizator yololy97Olaru Bogdan-Ioan yololy97 Data 15 februarie 2016 21:31:11
Problema Ubuntzei Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.95 kb
#include <cstdio>
#include <vector>
#include <queue>
#include <cstring>
#define N 2001
using namespace std;
int n, m;
struct nod {
    int u, cost;
    nod(){}
    nod(int _u, int _cost){
        u = _u;
        cost = _cost;
    }
};
vector<nod> a[N];
int prieten[20];
int K;
int d[N];
int cost[20][20];
int dp[(1 << 18) + 1][18];
void bellman(int startPos) {
    queue<int> Q;
    Q.push(prieten[startPos]);
    memset(d, 0x3f3f3f3f, sizeof(d));
    d[prieten[startPos]] = 0;
    while (!Q.empty()) {
        int u = Q.front();
        Q.pop();
        for(vector<nod>::iterator it = a[u].begin(); it != a[u].end(); ++it)
            if (d[u] + it->cost < d[it->u]) {
                d[it->u] = d[u] + it->cost;
                Q.push(it->u);
            }
    }
    for (int i = 0; i <= K + 1; ++i)
        if (i != startPos) {
            cost[i][startPos] = cost[startPos][i] = d[prieten[i]];
        }
}
void solve() {
    int i, j, conf;

    memset(dp, 0x3f3f3f3f, sizeof(dp));
    dp[1][0] = 0;

    for (conf = 0; conf < (1 << n); ++conf)
        for (i = 0; i < n; ++i)
            if (conf & (1 << i))
                for (j = 0; j < n; ++j)
                    if (i != j && conf & (1 << j)) {
                        dp[conf][i] = min(dp[conf - (1 << i)][j] + cost[i][j], dp[conf][i]);
                    }

    printf ("%d\n", dp[(1 << n) - 1][n - 1]);
}
int main() {
    int i, p, q, c;
    freopen("ubuntzei.in", "r", stdin);
    freopen("ubuntzei.out", "w", stdout);
    scanf ("%d %d\n", &n, &m);
    scanf ("%d ", &K);
    for (i = 1; i <= K; ++i)
        scanf ("%d ", &prieten[i]);
    prieten[0] = 1;
    prieten[K + 1] = n;

    while (m--) {
        scanf ("%d %d %d\n", &p, &q, &c);
        a[p].push_back(nod(q, c));
        a[q].push_back(nod(p, c));
    }

    for (i = 0; i <= K + 1; ++i) {
        bellman(i);
    }

    n = K + 2; // nodurile sunt acum de la 0 la K + 1

    solve();
}