Cod sursa(job #2952559)

Utilizator stefandutastefandutahoria stefanduta Data 9 decembrie 2022 15:30:12
Problema Ubuntzei Scor 20
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.06 kb
#include <fstream>
#include <vector>
#include <queue>
#define NMAX 2005
#define MMAX 10005

using namespace std;

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

struct ok{
    int vec, cost;
};

struct ok2{
    int nod, dist;
    bool operator < (ok2 a) const
    {
        return dist > a.dist;
    }
};

int c[NMAX];
vector <ok> adj[NMAX];
priority_queue <ok2> q;
int dist[NMAX][NMAX];
const int INF = 1e9 + 5;
const int PMAX = 132000;
const int KMAX = 18;
int dp[PMAX][KMAX];

int main()
{
    int n, m, k, i, j, a, b, x, l;
    in >> n >> m;
    in >> k;
    for (i = 1; i <= k; ++i)
        in >> c[i];
    c[0] = 1;
    c[k + 1] = n;

    for (i = 1; i <= m; ++i)
    {
        in >> a >> b >> x;
        adj[a].push_back({b, x});
        adj[b].push_back({a, x});
    }

    for (i = 1; i < NMAX; ++i)
    {
        for (j = 1; j < NMAX; ++j)
            dist[i][j] = INF;
    }

    for (j = 1; j <= n; ++j)
    {
        q.push({j, 0});
        dist[j][j] = 0;
        while(!q.empty())
        {
            int nod = q.top().nod;
            int d = q.top().dist;
            //out << nod << " " << d << '\n';
            q.pop();
            if (d == dist[j][nod])
            {
                for (i = 0; i < adj[nod].size(); ++i)
                {
                    int vec = adj[nod][i].vec;
                    int cost = adj[nod][i].cost;
                    if (dist[j][vec] > dist[j][nod] + cost)
                    {
                        dist[j][vec] = dist[j][nod] + cost;
                        dist[vec][j] = dist[j][nod] + cost;
                        q.push({vec, dist[j][nod] + cost});
                    }
                }
            }
        }
        dist[j][j] = INF;
    }

    int t =  1 << (k + 2);
    for (i = 0; i < t; ++i)
    {
        for (j = 0; j <= k + 1; ++j)
        {
            if (i <= 1)
                dp[i][j] = 0;
            else
                dp[i][j] = INF;
        }
    }

    //dp[0][0] = 0;
    //dp[1][0] = 0;

    for (i = 1; i < t; i = i + 2)
    {
        for (j = 0; j <= k + 1; ++j)
        {
            if (i & (1 << j))
            {
                for (l = 0; l <= k + 1; ++l)
                {
                    //out << i << " " << c[j] << " " << c[l] << " " << dp[i][j] << " " << dp[i ^ (1 << j)][l] + dist[c[l]][c[j]] << '\n';
                    if (dp[i][j] > dp[i ^ (1 << j)][l] + dist[c[l]][c[j]])
                    {
                        dp[i][j] = dp[i ^ (1 << j)][l] + dist[c[l]][c[j]];
                        //out << i << " " << c[j + 1] << " " << c[l + 1] << '\n';
                    }
                }
            }
        }
    }

    /*for (i = 1; i <= n; ++i)
    {
        for (j = 1; j <= n; ++j)
            out << dist[i][j] << " ";
        out << '\n';
    }*/
    /*out << '\n';

    for (i = 0; i < t; ++i)
    {
        for (j = 0; j <= k + 1; ++j)
            out << dp[i][j] << " ";
        out << '\n';
    }*/
    out << dp[t - 1][k + 1];

    return 0;
}