Pagini recente » Cod sursa (job #2067321) | Cod sursa (job #2208279) | Cod sursa (job #2382646) | Cod sursa (job #75055) | Cod sursa (job #2162382)
#include <iostream>
#include <fstream>
#include <vector>
#include <queue>
#include <bitset>
using namespace std;
const int oo = 2e9;
const int maxn = 2018;
int N, M, K;
int opriri[20];
int dist[2018][2018];
int dp[(1<<20)][20];
bitset <maxn> viz;
vector <pair <int, int> > G[maxn];
priority_queue <pair <int, int>,
vector<pair <int, int> >,
greater <pair <int, int> > > heap;
int main()
{
ifstream in ("ubuntzei.in");
ofstream out ("ubuntzei.out");
in>>N>>M>>K;
for(int i = 1; i <= K; ++i)
in>>opriri[i];
opriri[0] = 1;
opriri[K + 1] = N;
for(int i = 1; i <= M; ++i)
{
int x, y, z;
in>>x>>y>>z;
G[x].push_back(make_pair(y, z));
G[y].push_back(make_pair(x, z));
}
for(int i = 0; i <= K; ++i)
{
viz.reset();
for(int j = 1; j <= N; ++j)
dist[opriri[i]][j] = oo;
dist[opriri[i]][opriri[i]] = 0;
heap.push(make_pair(0, opriri[i]));
while(!heap.empty())
{
int nod = heap.top().second;
int d = heap.top().first;
heap.pop();
if(viz[nod])
continue;
viz[nod] = 1;
for(int k = 0; k < G[nod].size(); ++k)
if(dist[opriri[i]][G[nod][k].first] > d + G[nod][k].second)
{
dist[opriri[i]][G[nod][k].first] = d + G[nod][k].second;
heap.push(make_pair(d + G[nod][k].second, G[nod][k].first));
}
}
}
if (K == 0)
{
out << dist[1][N];
return 0;
}
//cout<<oo;
for(int i = 0; i < (1<<(K+1)); ++i)
for(int j = 0; j <= K; ++j)
dp[i][j] = oo;
dp[1][0] = 0;
//urmeaza ciclu hamiltonian
for(int conf = 0; conf < (1<<(K + 1)); ++conf)
for(int i = 0; i <= K; ++i)
if(conf & (1<<i))
for (int j = 0; j <= K; ++j)
if (j != i && (conf & (1<<j)))
dp[conf][i] = min (dp[conf][i], dp[conf ^ (1<<i)][j] + dist[opriri[j]][opriri[i]]);
int sol = oo;
for (int i = 0; i <= K; ++i)
{
//cout<<i<<" "<< dp[(1<<(K + 1)) - 1][i] + dist[opriri[i]][N];
sol = min(sol, dp[(1<<(K + 1)) - 1][i] + dist[opriri[i]][N]);
}
out<<sol;
return 0;
}