Cod sursa(job #2523002)

Utilizator petrisorvmyVamanu Petru Gabriel petrisorvmy Data 13 ianuarie 2020 17:21:06
Problema Ubuntzei Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.31 kb
#include <bits/stdc++.h>
#define Roc ios_base::sync_with_stdio(false), cin.tie(NULL)
#define ll long long
#define NMAX 2009
#define pi pair<int,int>
using namespace std;

ifstream f("ubuntzei.in");
ofstream g("ubuntzei.out");

int n, m, k, town[20], pd[1 + (1 << 17)][20 + 1],distT[20][NMAX], distP[NMAX];
vector < pi > G[NMAX];


void Dijkstra(int start, int d[NMAX])
{
    set <pi> Q;
    for(int i = 1; i <= n; ++i)
        d[i] = 1 << 26;
    d[start] = 0;
    Q.insert({0, start});
    while(!Q.empty())
    {
        int nod = (*Q.begin()).second;
        Q.erase(Q.begin());
        for(auto it : G[nod])
            if(d[nod] + it.second < d[it.first])
            {
                if(d[it.first] != 1 << 26)
                    Q.erase( Q.find({d[it.first] , it.first}) );
                d[it.first] = d[nod] + it.second;
                Q.insert({d[it.first], it.first});
            }
    }
}

int main()
{
    Roc;
    f >> n >> m >> k;
    for(int i = 1; i <= k; ++i)
        f >> town[i];
    for(int i = 1; i <= m; ++i)
    {
        int x, y, c;
        f >> x >> y >> c;
        G[x].push_back({y,c});
        G[y].push_back({x,c});
    }
    Dijkstra(1,distP);
    /*
    for(int i = 1; i <= n; ++i)
        g << distP[i] << ' ';
    g << '\n';
    */
    if(k == 0)
        g << distP[n];
    else
    {
        for(int i = 1; i <= k; ++i)
            Dijkstra(town[i], distT[i]);
        int W = (1 << k) - 1;
        for(int i = 0; i <= W ; ++i)
            for(int j = 0; j <= k; ++j)
                pd[i][j] = (1 << 26);


        for(int i = 1; i <= W; ++i)
            for(int j = 1; j <= k; ++j)
                if( (i & (1 << (j-1)) ) != 0 )
                {
                    int ant = i - (1 << (j-1));
                    if(ant == 0)
                        pd[i][j] = distP[ town[j] ];
                    else
                        for(int q = 1; q <= k; ++q)
                        pd[i][j] = min(pd[i][j], pd[ant][q] + distT[q][town[j]]);
                }

        int ans = 1 << 26;
        for(int i = 1; i <= k; ++i)
        {
            ans = min(ans, pd[W][i] + distT[i][n]);
          ///  g << pd[W][i] << ' ';
          ///  g << '\n';
        }
        g << ans;
    }
    f.close();
    g.close();
    return 0;
}