Pagini recente » Cod sursa (job #198663) | Cod sursa (job #2936456) | Cod sursa (job #554290) | Rating Irina Tenita (baaja) | Cod sursa (job #2301805)
/*
* Giving the Linus Torvalds Award to the Free Software Foundation
* is a bit like giving the Han Solo Award to the Rebel Alliance.
* - Richard M. Stallman
*/
#include <fstream>
#include <vector>
#include <queue>
#include <memory>
const int INF = 1 << 28;
const int MAX_K = 17;
struct Edge
{
int from, to;
int cost;
};
std::vector<int> dijkstra(const std::vector<std::vector<Edge>> &graph, int nNodes, int startNode)
{
std::vector<int> result;
std::vector<int> &distances = result;
std::vector<bool> was;
std::priority_queue<std::pair<int, int>, std::vector<std::pair<int, int>>, std::greater<std::pair<int, int>>> pq;
distances.insert(distances.begin(), static_cast<unsigned long>(nNodes), INF);
was.insert(was.begin(), static_cast<unsigned long>(nNodes), false);
distances[startNode] = 0;
pq.push({distances[startNode], startNode});
while(!pq.empty())
{
while(!pq.empty() && was[pq.top().second])
pq.pop();
if(!pq.empty())
{
int x = pq.top().second;
was[x] = true;
pq.pop();
for(auto edge: graph[x])
{
if(distances[x] + edge.cost < distances[edge.to])
{
distances[edge.to] = distances[x] + edge.cost;
pq.push({distances[edge.to], edge.to});
}
}
}
}
return std::move(result);
}
int cost[MAX_K][MAX_K];
int d[1 << MAX_K][MAX_K];
constexpr int count_bits(int i)
{
return (1 & i) + (2 & i) + (4 & i) + (8 & i) + (16 & i) + (32 & i) + (64 & i) + (128 & i) + (256 & i) + (512 & i) +
(1024 & i) + (2048 & i) + (4096 & i) + (8192 & i) + (16384 & i) + (32768 & i) + (65536 & i) + (131072 & i) +
(262144 & i) + (524288 & i) + (1048576 & i) + (2097152 & i) + (4194304 & i) + (8388608 & i) +
(16777216 & i) + (33554432 & i) + (67108864 & i) + (134217728 & i) + (268435456 & i) + (536870912 & i) +
(1073741824 & i);
}
int main()
{
std::ifstream fin("ubuntzei.in");
int n, m, k;
std::vector<int> pointsOfInterest;
std::vector<std::vector<Edge>> graph;
fin >> n >> m >> k;
pointsOfInterest.insert(pointsOfInterest.begin(), static_cast<unsigned long>(k + 2), {});
pointsOfInterest[0] = 0;
pointsOfInterest[k + 1] = n - 1;
for(int i = 1; i <= k; i++)
fin >> pointsOfInterest[i], pointsOfInterest[i]--;
graph.insert(graph.begin(), static_cast<unsigned long>(n), {});
for(int i = 0; i < m; i++)
{
int x, y, z;
fin >> x >> y >> z;
x--; y --;
graph[x].push_back({x, y, z});
graph[y].push_back({y, x, z});
}
for(int i = 0; i < k + 2; i++)
for(int j = 0; j < k + 2; j++)
cost[i][j] = i == j ? 0 : INF;
for(int i = 0; i < pointsOfInterest.size(); i++)
{
auto d = std::move(dijkstra(graph, n, pointsOfInterest[i]));
for(int j = 0; j < pointsOfInterest.size(); j++)
cost[i][j] = d[pointsOfInterest[j]];
}
int nn = k + 2;
for(int i = 0; i < (1 << nn); i++)
for(int j = 0; j < nn; j++)
d[i][j] = INF;
d[1][0] = 0;
for(int i = 1; i < (1 << nn); i += 2)
for(int j = 1; j < nn; j++)
for(int k = 0; k < nn; k++)
if(((1 << k) & i) != 0 && k != j)
{
d[i][j] = std::min(d[i][j], d[i ^ (1 << j)][k] + cost[k][j]);
}
std::ofstream fout("ubuntzei.out");
fout << d[(1 << nn) - 1][nn - 1];
return 0;
}