迪杰斯特拉C++

迪杰斯特拉单源点最短路径算法
从起始点开始,采用贪心算法的策略,
每次遍历到始点距离最近且未访问过的顶点的邻接节点,直到扩展到终点为止。

#include<iostream>
#include<vector>


using namespace std;

/*
6
0 0 10 0 30 100
0 0 5  0  0  0
0 0 0  50 0  0
0 0 0  0  0  10
0 0 0  20 0  60
0 0 0  0  0  0

5
0 10 0 0 5
0 0  1 0 2
0 0  0 4 0
7 0  6 0 0
0 3  9 2 0

从起始点开始,采用贪心算法的策略,
每次遍历到始点距离最近且未访问过的顶点的邻接节点,直到扩展到终点为止。
*/

const int inf = 1e9;

int main()
{
	int n;
	cin >> n;
	vector<vector<int>> map(n, vector<int>(n));
	for (auto& x : map)
	{
		for (auto& a : x)
		{
			cin >> a;
			if (a == 0)
				a = inf;
		}
	}

	for (auto& x : map)
	{
		for (auto& a : x)
			cout<< a<<" ";
		cout << '\n';
	}
	vector<bool> final(n);//标记是否已找到最短路径
	vector<int> dist(n,inf);//最短路径长度
	vector<int> path(n,-1);//路径上的前驱

	/*
	* Dijkstra算法:单元点最短路径
	* 从结点0出发,进行扩展,在dist上找到最小的距离,此节点的前去就是节点0
	* 再进行以刚才最短路径的结点来作为源点继续扩展
	*/
	int cnt = 1;//已被访问结点
	int begin = 0;//起点为0
	final[0] = true;//标记起点已访问
	path[0] = -1;
	dist[0] = 0;
	for (int i = 0; i < n; ++i)
	{
		if (!final[i]&&map[begin][i] > 0)
		{
			dist[i] = map[begin][i];
			path[i] = begin;
		}
	}//初始化起点数据


	while (1)
	{
		int min_pos = -1;
		for (int i = 0; i < n; ++i)
		{
			if (!final[i] && (min_pos == -1 || dist[i] < dist[min_pos]))
			{
				min_pos = i;
			}
		}
		begin = min_pos;
		final[min_pos] = true;//结点min_pos的最短路径找到
		cnt++;
		if (cnt == n)//所有节点都扩展了,break
			break;

		for (int i = 0; i < n; i++)
		{
			if (!final[i]&&dist[i] > dist[begin] + map[begin][i])
			{//如果当前有节点的新路径距离小于之前的路径,更新该节点的dist和path
				dist[i] = dist[begin] + map[begin][i];
				path[i] = begin;//更新该节点的前驱
			}
		}
	}


	cout << "dist[" << n << "] = ";
	for (auto x : dist)
		cout << x << " " ;
	cout << endl;
	cout << "path[" << n << "] = ";
	for (auto x : path)
		cout << x << " ";
	cout << endl;

	return 0;
}

总结:
算法理解不难,要初始化的条件很多,最后输出的结果页不明显

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值