Pagini recente » Cod sursa (job #611132) | Cod sursa (job #2177896) | Cod sursa (job #763108) | Cod sursa (job #2871929) | Cod sursa (job #1011201)
#include <iostream>
#include <fstream>
#include <vector>
#include <queue>
#include <bitset>
#include <string.h>
#include <algorithm>
#define IN "ubuntzei.in"
#define OUT "ubuntzei.out"
#define MAX_N 205
#define MAX_K 15
#define oo 10000
using namespace std;
ifstream f(IN);
ofstream g(OUT);
int N, M, K, u, v, cost;
int dist[MAX_N][1 << MAX_K], rf[MAX_N][MAX_N];;
bitset< (1 << MAX_K) > inque[MAX_N];
queue < pair < int, int > > Q;
vector < int > adj[MAX_N], subset, idxSubset;
bitset < MAX_N > inSubset;
inline void READ_DATA()
{
f >> N >> M >> K;
subset.resize(K);
idxSubset.resize(N);
idxSubset.assign(idxSubset.size(), -1);
for (int i = 0; i < K; ++ i)
{
f >> u; -- u;
subset[i] = u;
idxSubset[u] = i;
inSubset[u] = true;
}
for (int i = 0; i < M; ++ i)
{
f >> u >> v >> cost;
-- u, -- v;
rf[u][v] = rf[v][u] = cost;
}
}
inline void RF()
{
for (int k = 0; k < N; ++ k)
for (int i = 0; i < N; ++ i)
for (int j = 0; j < N; ++ j)
rf[i][j] = min(rf[i][j], rf[i][k] + rf[k][j]);
}
void SOLVE()
{
if (K > 0)
{
for (int i = 0; i < N; ++ i)
for (int j = i + 1; j < N; ++ j)
if ((inSubset[i] || !i || i == N - 1) && (inSubset[j] || !j || j == N - 1))
{
adj[i].push_back(j);
adj[j].push_back(i);
}
memset(dist, oo, sizeof(dist));
dist[0][0] = 0;
Q.push(make_pair(0, 0)), inque[0][0] = true;
while (!Q.empty())
{
int u = Q.front().first;
int s = Q.front().second;
Q.pop();
inque[u][s] = false;
for (vector <int>::iterator it = adj[u].begin(); it != adj[u].end(); ++ it)
{
int v = *it;
if (!inSubset[v])
{
if (dist[v][s] > dist[u][s] + rf[u][v])
{
dist[v][s] = dist[u][s] + rf[u][v];
if (inque[v][s] == false)
{
Q.push(make_pair(v, s));
inque[v][s] = true;
}
}
}
else
if (!(s & (1 << idxSubset[v])))
{
int t = s | (1 << idxSubset[v]);
if (dist[v][t] > dist[u][s] + rf[u][v])
{
dist[v][t] = dist[u][s] + rf[u][v];
if (inque[v][t] == false)
{
Q.push(make_pair(v, t));
inque[v][t] = true;
}
}
}
}
}
int sink = N - 1;
int conf = (1 << subset.size()) - 1;
g << dist[sink][conf] << "\n";
}
else
g << rf[0][N - 1] << "\n";
}
int main(void)
{
memset(rf, oo, sizeof(rf));
for (int i = 0; i < N; ++ i)
rf[i][i] = 0;
READ_DATA();
RF();
SOLVE();
g.close();
return 0;
}