zoukankan      html  css  js  c++  java
  • 迪杰斯特拉算法学习

    转自:https://zhuanlan.zhihu.com/p/40338107

    1.介绍

    迪杰斯特拉(Dijkstra)算法是典型最短路径算法,用于计算一个节点到其他节点的最短路径。它的主要特点是以起始点为中心向外层层扩展(广度优先搜索思想),直到扩展到终点为止。

    但它不能处理负权路径,如果先找到一条不为负的最短,但当前目标节点已经被访问过,就无法更新包括负权的路径了。

    2.基本过程

    • 指定起点s,定义两个集合S、U,其中S表示已经求出最短路径的节点,U表示待求的
    • 初始时S中只有s节点,从U中选取出距离最近的加入,并且更新U中其他节点经过u到s的最短距离。
    • 直到所有节点都被访问完。

    3.实现

    https://blog.csdn.net/qq_35644234/article/details/60870719

    void Graph_DG::Dijkstra(int begin){
        //首先初始化我们的dis数组
        int i;
        for (i = 0; i < this->vexnum; i++) {
            //设置当前的路径
    //begin默认为0,更新直接相连的为默认距离
            dis[i].path = "v" + to_string(begin) + "-->v" + to_string(i + 1);
            dis[i].value = arc[begin - 1][i];
        }
        //设置起点的到起点的路径为0
        dis[begin - 1].value = 0;
        dis[begin - 1].visit = true;//标记初始节点访问过
    
        int count = 1;
        //计算剩余的顶点的最短路径(剩余this->vexnum-1个顶点)
        while (count != this->vexnum) {
            //temp用于保存当前dis数组中最小的那个下标
            //min记录的当前的最小值
            int temp=0;
            int min = INT_MAX;
            for (i = 0; i < this->vexnum; i++) {//选择距离最小的顶点
                if (!dis[i].visit && dis[i].value<min) {
                    min = dis[i].value;
                    temp = i;
                }
            }
            //cout << temp + 1 << "  "<<min << endl;
            //把temp对应的顶点加入到已经找到的最短路径的集合中
            dis[temp].visit = true;//标记已找到最小距离
            ++count;
            for (i = 0; i < this->vexnum; i++) {
                //注意这里的条件arc[temp][i]!=INT_MAX必须加,不然会出现溢出,从而造成程序异常
                if (!dis[i].visit && arc[temp][i]!=INT_MAX && (dis[temp].value + arc[temp][i]) < dis[i].value) {
                    //如果新得到的边可以影响其他为访问的顶点,那就就更新它的最短路径和长度
                    dis[i].value = dis[temp].value + arc[temp][i];
                    dis[i].path = dis[temp].path + "-->v" + to_string(i + 1);
                }
            }
        }
    }

    4.时空复杂度

    https://www.cnblogs.com/gaochundong/p/dijkstra_algorithm.html

    m为边数,n为节点数,如果用邻接矩阵存储,并且只使用普通的数组存储距离的话,那么时间复杂度为O(n^2)。

    下图中V是顶点数目,E是边:

    //不太明白binary heap和斐波那契堆是什么。

  • 相关阅读:
    关于这个 blog
    P6499 [COCI2016-2017#2] Burza 题解
    CF1172F Nauuo and Bug 题解
    CF1479D Odd Mineral Resource 题解
    CF1442E Black, White and Grey Tree 题解
    CF1442D Sum 题解
    CF1025D Recovering BST 题解
    CF1056E Check Transcription 题解
    CF1025F Disjoint Triangles 题解
    红包算法的PHP实现
  • 原文地址:https://www.cnblogs.com/BlueBlueSea/p/14356365.html
Copyright © 2011-2022 走看看