Pagini recente » Cod sursa (job #2500191) | Cod sursa (job #224600) | Cod sursa (job #557511) | Cod sursa (job #1082012) | Cod sursa (job #3121319)
#include <fstream>
#include <vector>
#include <queue>
#include <map>
using namespace std;
// ifstream cin("input"); ofstream cout("output");
ifstream cin("ubuntzei.in"); ofstream cout("ubuntzei.out");
const int inf = 2e9;
int n, m, k;
vector<int> prieten;
vector<vector<pair<int,int>>> gr;
priority_queue<pair<int, int>, vector<pair<int, int>>, greater<>> Q;
vector<int> distanta;
vector<vector<int>> min_dist;
vector<vector<int>> dp;
void read() {
cin >> n >> m;
gr.resize(n + 1);
distanta.resize(n+1);
cin >> k;
prieten.resize(k+1);
min_dist.resize(k+2, vector<int>(k+2, inf));
dp.resize((1 << k), vector<int>(k+1));
for (int i = 1; i <= k; i++) {
cin >> prieten[i];
}
for (int i = 1; i <= m; i++) {
int a, b, val;
cin >> a >> b >> val;
gr[a].push_back({b, val});
gr[b].push_back({a, val});
}
}
void dijkstra(int root, bool nu_am_prieteni = false) {
for (int i = 1; i <= n; i++) {
distanta[i] = inf;
}
if (nu_am_prieteni){
Q.push({1, 0});
distanta[1] = 0;
}
else{
Q.push({prieten[root], 0});
distanta[prieten[root]] = 0;
}
while (!Q.empty()) {
pair<int, int> now = Q.top();
Q.pop();
if (distanta[now.first] != now.second) {
continue;
}
for (auto &x : gr[now.first]) {
if (distanta[x.first] > now.second + x.second) {
distanta[x.first] = now.second + x.second;
Q.push({x.first, distanta[x.first]});
}
}
}
min_dist[root][0] = distanta[1];
min_dist[root][k + 1] = distanta[n];
for (int i = 1; i <= k; i++) {
min_dist[root][i] = distanta[prieten[i]];
}
}
void solve() {
if (k == 0) {
dijkstra(1, true);
cout << distanta[n];
return;
}
for (int i = 1; i <= k; i++) {
dijkstra(i);
}
for (int mask = 0; mask < (1 << k); mask++) {
for (int last = 0; last < k; last++) {
dp[mask][last] = inf;
}
}
dp[0][0] = 0;
for (int mask = 0; mask < (1 << k); mask++) {
for (int last = 0; last < k; last++) {
if (dp[mask][last] == inf) {
continue;
}
for (int bit = 0; bit < k; bit++) {
if ((1 << bit) & mask) {
continue;
}
if (mask == 0) {
if (min_dist[bit + 1][0] != inf) {
dp[mask ^ (1 << bit)][bit] = min(dp[mask ^ (1 << bit)][bit], min_dist[bit + 1][0]);
}
continue;
}
if (min_dist[last + 1][bit + 1] != inf) {
dp[mask ^ (1 << bit)][bit] = min(dp[mask ^ (1 << bit)][bit],
dp[mask][last] + min_dist[last + 1][bit + 1]);
}
}
}
}
int ans = inf;
for (int i = 0; i < k; i++) {
if (min_dist[i + 1][k + 1] != 0) {
ans = min(ans, dp[(1 << k) - 1][i] + min_dist[i + 1][k + 1]);
}
}
cout << ans;
}
int main() {
read();
solve();
}