单源最短路径
BFS方法(无权图)
void BFS_MIN_Distance(Graph G, int u){
for(i=0;i<G.vexnum;++i){
d[i]=∞;
path[i]=-1;
}
d[u]=0;
visited[u]=TRUE;
EnQuene(Q,u);
while(!isEmpty(Q)){
DeQueue(Q,u);
for(w=FirstNeighbor(G,u);w>=0;w=NextNeighbor(G,u,w)){
if(!visited[w]){
d[w]=d[u]+1;
path[w]=u;
visited[w]=TRUE;
EnQueue(Q,w);
}
}
}
}
Dijkstra算法(带权图、无权图)
总共三个数组,分别存储各顶点是否已找到最短路径、最短路径长度、路径上的前驱。
分别对应下方代码的visited[n]、dist[n]、pred[]。
初始: 若从Vo开始,令final[0]=true; dist[0]=0; path[0]=-1。其余顶点final[k]=false; dist[k]=arcs[0][k]; path[k]= (arcs[0][k]==∞) ? -1 :0
n-1轮处理:循环遍历所有顶点,找到还没确定最短路径,且dist 最小的顶点Vi,令final[i]=true。并检查所有邻接自Vi的顶点,对于邻接自Vi的顶点Vj,若final==false 且 dist[i]+arcs[i][j] < dist[j],则令 dist[j]=dist[i]+arcs[i][j]; path[j]=i。 (注: arcs[i][j]表示Vi到Vj的弧的权值)
#include <iostream>
#include <limits.h>
using namespace std;
// 定义一个表示无穷大的常量
#define INF INT_MAX
// n 为图的顶点数,src 为源点
void dijkstra(int graph[][10], int n, int src) {
bool visited[n]; // 标记各顶点是否已找到最短路径
int dist[n]; // 记录最短路径的长度
int pred[n]; // 记录路径上的前驱
// 初始化 visited, dist, pred 数组
for (int i = 0; i < n; i++) {
visited[i] = false;
dist[i] = INF;
pred[i] = -1;
}
// 将起点到自己的距离设置为 0
dist[src] = 0;
// 找到从起点到其它所有顶点的最短路径
for (int i = 0; i < n - 1; i++) {
// 找到距离起点最近的顶点
int minDist = INF, minIndex;
for (int j = 0; j < n; j++) {
if (!visited[j] && dist[j] < minDist) {
minDist = dist[j];
minIndex = j;
}
}
// 标记该顶点为已找到最短路径
visited[minIndex] = true;
// 更新与该顶点相邻的顶点的最短路径
for (int j = 0; j < n; j++) {
int newDist = graph[minIndex][j] + dist[minIndex];
if (!visited[j] && graph[minIndex][j] && newDist < dist[j]) {
dist[j] = newDist;
pred[j] = minIndex;
}
}
}
// 输出结果
cout << "顶点\t最短距离\t路径" << endl;
for (int i = 0; i < n; i++) {
cout << i << "\t" << dist[i] << "\t\t" << i;
int j = i;
while (j != src) {
cout << "<-" << pred[j];
j = pred[j];
}
cout << endl;
}
}
int main() {
int n = 6; // 图的顶点数
int graph[10][10] = { // 图的邻接矩阵
{0, 1, 4, 0, 0, 0},
{1, 0, 2, 5, 0, 0},
{4, 2, 0, 1, 3, 0},
{0, 5, 1, 0, 2, 6},
{0, 0, 3, 2, 0, 4},
{0, 0, 0, 6, 4, 0}
};
int src = 0; // 源点
dijkstra(graph, n, src);
return 0;
}
/*
顶点 最短距离 路径
0 0 0
1 1 1<-0
2 3 2<-1<-0
3 4 3<-2<-1<-0
4 6 4<-2<-1<-0
5 10 5<-3<-2<-1<-0
*/