模板 - Dijkstra
题目链接 :畅通工程续
这个算法是最短路中可操作性最强的一种了,使用了for循环,可以保证没个点只会经过一次,在这个基础上,我们可以保存最短路径,甚至,还可以保存满足条件的次短路L2-001. 紧急救援 。而且在出现了重边时,这时可以快速的处理。如果用了vector就会很麻烦。
代码
#include <iostream>
#include <cstring>
#include <set>
using namespace std;
#define rep(i,j,k) for(int i = j;i <= k;i ++)
#define per(i,j,k) for(int i = j;i >= k;i --)
typedef long long ll;
const int MAXN = (int) 2007 ;
const int INF = (int)0x3f3f3f3f;
int G[MAXN][MAXN];
int dis[MAXN];
int vis[MAXN];
void init(){
memset(dis,0x3f,sizeof(dis));
memset(G,0x3f,sizeof(G));
memset(vis,0,sizeof(vis));
}
int main()
{
ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
int N,M;
while (cin >> N >> M){
init();
int x,y,w;
rep(i,0,M-1) {
cin >> x >> y >> w;
if (w >= G[x][y]) continue;
G[x][y] = G[y][x] = w;
}
int S,E;
cin >> S >> E;
dis[S] = 0;
int now;
rep(j,0,N-1) {
int mn = INF;
int index = -1;
rep(i,0,N-1){
if (mn > dis[i] && !vis[i]){
mn = dis[i];
index = i;
}
}
if (index == -1)break;
now = index;
vis[index] = 1;
rep(i,0,N-1){
if (dis[i] > G[now][i] + dis[now]){
dis[i] = G[now][i] + dis[now];
}
}
}
if (dis[E] == INF)cout << -1 << endl;
else cout << dis[E] << endl;
}
}