Dijkstra

Posted longxue1991

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Dijkstra相关的知识,希望对你有一定的参考价值。

#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 500;
int n, m, g[N][N], d[N];
bool st[N];
int dijkstra()
{
    memset(d, 0x3f, sizeof d);//两点之间和1到n-1个点之间的初始值都为+oo
    d[1] = 0;
    for(int i = 0;i<n;i++)
    {
        int t = -1;
        for(int j = 1;j<=n;j++)
            if(!st[j] && (t == -1 || d[t] > d[j]))
                t = j;
        st[t] = true;
        
        for(int j = 1; j <= n;j++)
            d[j] = min(d[j], d[t] + g[t][j]);
    }
    if(d[n] == 0x3f3f3f3f) return -1;
    
    return d[n];
}
int main()
{
    memset(g, 0x3f, sizeof g);
    cin>>n>>m;
    for(int i = 0; i < n; i++)
    {
        int a, b, c;
        cin>>a>>b>>c;
        g[a][b] = min(g[a][b], c);
    }
    cout<<dijkstra()<<endl;
}

起始点为1,1到自己的距离d[1] = 0; 走过的点就打好标记不再考虑了,st[t]  = true;

任意两点之间和1到n-1个点之间的初始值都为无穷大+oo,g[]和d[]
每次向后拓展的时候都选择当前最短的边:d[t] > d[j] t = j;
若后面的点更新有更小的距离,那么就进行更新:d[j] = min(d[j], d[t] + g[t][j]);
注意Dijkstra如果有n个点的话,那么就要循环n次,也就是说,n个点没有负权的图(可以有自环和重边),通过跑n次Dijkstra一定可以跑出1到其他n-1个点的最短距离。
为什么如果有负权边不能用Dijkstra呢?因为如果有负数环的话,每跑一次距离就变小一次。。。
1n5001≤n≤500,
1m1051≤m≤105,
图中涉及边长均不超过10000。

此题点数较少,变数较多称为稠密图。上面的邻接矩阵版本是朴素的裸Dijkstra算法。
但是如果数据范围是:

数据范围

1n,m1.5×1051≤n,m≤1.5×105,
图中涉及边长均不小于0,且不超过10000。

那么就是稀疏图,如果还是用上面的邻接矩阵的话,10^5 * 10 ^ 5会爆掉。

那么就要用堆优化版本的Dijkstra算法。

以上是关于Dijkstra的主要内容,如果未能解决你的问题,请参考以下文章

1.Dijkstra算法求解格栅地图路径matlab代码

1.Dijkstra算法求解格栅地图路径matlab代码

1.Dijkstra算法求解格栅地图路径matlab代码

计算图的最短距离--Dijkstra算法

如何将此代码从 Dijkstra 转换为 Astar?

java代码实现Dijkstra算法求图的最短路径