题目传送门:http://acm.hdu.edu.cn/showproblem.php?pid=2066
这题我刚开始用迪杰斯特拉算法做的,结果超时了,下面用优先队列+迪杰斯特拉算法做的,用邻接矩阵保存的图.
AC代码:
#include <iostream>
#include <algorithm>
#include <vector>
#include <functional>
#include <queue>
using namespace std;
#define Size 1001
#pragma warning (disable : 4996)
const int inf = 0x3f3f3f3f;
struct Node
{
int pos;
int time;
bool operator < (Node a) const
{
return this->time > a.time;
}
Node(int a, int b)
{
pos = a;
time = b;
}
Node() = default;
};
int T, S, D;
int a, b, c;
vector<Node> world[Size];
vector<int> adjacent;
vector<int> want;
int dist[Size];
int visit[Size];
void dijkstra()
{
priority_queue<Node> temp;
//把相邻的城市放到优先队列里去.
for (int i = 0; i < adjacent.size(); ++i)
{
Node s;
s.pos = adjacent[i];
s.time = 0;
dist[s.pos] = 0;
temp.push(s);
}
while (!temp.empty())
{
Node now = temp.top();
temp.pop();
//判断是否访问过.
if (visit[now.pos] == 1)
continue;
visit[now.pos] = 1;
for (int i = 0; i < world[now.pos].size(); ++i)
{
Node next = world[now.pos][i];
//判断距离是否更小.则修改最小距离.
if (now.time + next.time < dist[next.pos])
{
dist[next.pos] = now.time + next.time;
temp.push(Node(next.pos, dist[next.pos]));
}
}
}
}
int main()
{
while (scanf("%d%d%d", &T,&S,&D) != EOF)
{
for (int i = 0; i < Size; ++i)
{
world[i].clear();
}
for (int i = 0; i < Size; ++i)
{
dist[i] = inf;
}
memset(visit,0,sizeof(visit));
adjacent.clear();
want.clear();
for (int i = 0; i < T; ++i)
{
scanf("%d%d%d", &a, &b, &c);
//把路径放到邻接矩阵里去.
world[a - 1].push_back(Node(b - 1, c));
world[b - 1].push_back(Node(a - 1, c));
}
for (int i = 0; i < S; ++i)
{
scanf("%d", &a);
//保存相邻的地方.
adjacent.push_back(a - 1);
}
for (int i = 0; i < D; ++i)
{
scanf("%d", &a);
//保存想要去的地方.
want.push_back(a - 1);
}
dijkstra();
int minL = inf;
for (int i = 0; i < want.size(); ++i)
{
minL = min(minL, dist[want[i]]);
}
printf("%d\n", minL);
}
return 0;
}