贪心算法——单源最短路径(Dijkstra算法)
来源:互联网 发布:exe一机一码加密软件 编辑:程序博客网 时间:2024/05/16 14:31
关于贪心算法介绍:
http://blog.csdn.net/mind_v/article/details/72956707
单源最短路径——Dijkstra算法
问题描述
对于给定的加权有向图G(加权邻接数组表示),它的每一条边(i,j)都有一个固定成本(权值)a[i][j],一条路径的长度就是该路径上所有边的的成本之和。如下图所示,路径124的长度是8,路径125的长度是9。
寻找一条从给定的一个源顶点出发到任意顶点的(目的顶点)的最短路径。如1到5的最短路径为1345。
贪心法求解
根据贪婪法,每一步生成一条当前顶点的最短路径。每一条最短路径的目的顶点的选择方法依据贪婪准则:从一条最短路径还没有到达的顶点中,选择一个可以产生最短路径的目的顶点。
我们定义distanceFromSource[i]是在已生成的最短路径上再拓展一条最短边而到达顶点i时的最短路径长度。最开始,只有一条从sourceVertex到sourceVertex的路径,长度为0。这是对于每一个顶点,distanceFromSource[i]等于a[sourceVertex][i]。为产生下一条路径,需要选择一个还没最短路径到达的顶点,在这些顶点中,使distanceFromSource[]值最小的顶点就是下一条路径的终点。当得到一条最短路径之后,有些顶点的的distanceFromSource[]值可能会改变,因为由新的最短路径拓展可能得到更小的值。
算法步骤:
1)初始化distanceFromSource[i]=a[sourceVertex][i]
(1<= i <= n)
对所有邻接于sourceVertex
的顶点i,令prodecesoor[i]=sourceVertex
对所有的其他顶点,predecessor[sourceVertex]=0,predecessor[i]=-1
创建一个newReachableVertices
,存储所有predecessor[i]>0
的顶点(即这个表包含所有邻接于sourceVertex
的顶点)。
2)如果newReachableVertices
为空,算法终止,否则转置3)
3)从newReachableVertices
中删除distanceFromSource
值最小的i
4)对所有邻接于i的顶点j,将distanceFromSource[j]
更新min{distanceFromSource[j],distanceFromSource[i]+a[i][j]}。如果
distanceFromSource[j]改变,令
predecessor[j]=i,而且若j没有在
newReachableVertices`中,则将其加入进去。
注:newReachableVertices是一个链表对象,使用到的接口包括:
insert(index, element):在指定索引位置插入元素element的节点;
eraseElement(element):删除指定的元素节点;
begin():返回第一个元素的迭代器
end():返回最后一个元素后一个位置的迭代器
C++实现:
void shortestPaths(int sourceVertex, int *distanceFromSource, int numberOfVertices){//寻找从源顶点开始的最短路径 //从数组distanceFromSource中返回最短路径 //在数组predecessor中返回顶点在路径上的前驱的信息 if (sourceVertex < 1 || sourceVertex > n) throw illegalParameterValue("Invalid source Vertex"); //确定是加权图 if (!weighted()) return; chain<int> newReachableVertices; for (int i = 1; i <= n; ++i) { distanceFromSource[i] = a[sourceVertex][i]; if (distanceFromSource[i] == noEdge) distanceFromSource[i] = -1; else { predecessor[i] = sourceVertex; newReachableVertices.insert(0, i); } } distanceFromSource[sourceVertex] = 0; Predecessor[sourceVertex] = 0; //更新distanceFromSource和predecessor while (!newReachableVertices.empty()) {//还存在更多的路径 //寻找distanceFromSource值最小的,还未达到的顶点v chain<T>::iterator iNewReachableVertices = newReachableVertices.begin(); chain<T>::iterator end = newReachableVertices.end(); int v = *iNewReachableVertices; iNewReachableVertices++; while (iNewReachableVertices != end) { int w = *iNewReachableVertices; iNewReachableVertices++; if (distanceFromSource[w] < distanceFromSource[v]) v = w; } //下一条最短路径到达v //先从newReachableVertices中删除v,然后更新distanceFromSource for (int j = 1; j <= n; ++j) { if (a[v][j] != noEdge && (predecessor[j] == -1 || distanceFromSource[j] > distanceFromSource[v] + a[v][j])) { //distanceFromSource[j]减少 distanceFromSource[j] = distanceFromSource[v] + a[v][j]; if (predecessor[j] == -1) //以前未到达,加入j newReachableVertices.insert(0, j); predecessor[j] = v; } } }}
使用邻接矩阵描述图时,第一个while循环的复杂度为O(n),第二个while循环和for循环都要达到所有的顶点,故也为O(n),所以整个算法的时间复杂度为O(n2)。
- 贪心算法——单源最短路径(Dijkstra算法)
- 贪心算法——单源最短路径 dijkstra
- 贪心算法——单源最短路径 dijkstra
- 单源最短路径(Dijkstra)——贪心算法
- 贪心算法------单源最短路径问题(Dijkstra)
- 单源最短路径(Dijkstra算法)贪心策略
- 贪心算法--Dijkstra单源最短路径
- 贪心算法 - 单源最短路径 Dijkstra
- 贪心算法 Dijkstra 单源最短路径
- 贪心算法-Dijkstra单源最短路径
- 贪心算法 - 单源最短路径 Dijkstra
- 贪心算法--Dijkstra算法(单源最短路径算法)
- 贪心算法——单源最短路径 dijkstra 收藏
- Dijkstra算法|单源最短路径|贪心算法
- 贪心算法实例 单源最短路径 Dijkstra算法(c++实现)
- 贪心算法之单源最短路径(Dijkstra算法)
- 单源最短路径---贪心法实现(Dijkstra算法)
- 单源最短路径---贪心法实现(Dijkstra算法)
- 数字图像基本处理算法
- 模p平方根算法实现
- 洛谷 2420 让我们异或吧
- CCF 图像旋转
- HDU-1016 Prime Ring Problem
- 贪心算法——单源最短路径(Dijkstra算法)
- 关于Ajax的跨域问题
- Struts2自定义拦截器
- Mybatis多环境数据源配置方式之environment标签
- Java 多线程并发编程之互斥锁 Reentrant Lock
- Android TP 驱动之(一)I2C
- HDU 4908 BestCoder Sequence 思维
- SDUT-3345 数据结构实验之二叉树六:哈夫曼编码
- 一些 快速 有用的 函数