dijkstra的堆优化(最简版本)

dijkstra的堆优化(最简版本)

先了解不用堆优化的dijkstra:https://blog.csdn.net/weixin_43828245/article/details/90722389
推荐视频讲解(代码是Python写的,重点听思路):https://www.bilibili.com/video/av25829980
了解c++优先队列:https://blog.csdn.net/weixin_43828245/article/details/90742490

直接放代码,详见注释

#include 
#include 
#include 

#define inf 0x3f3f3f

using namespace std;

typedef struct node {
    int v,date;
} ty;

bool operator < ( const ty &a, const ty &b ) // 自定义优先队列规则,先pop出小的来
{
    return a.date>b.date;  // 这里和sort相反,a>b是先pop出小的
}

int a[2002][2002];
int via[2002];  // 判断是否已经pop出来了
int dis[2002];  // 存放距离
int i,j,n,m;
ty t,d;

void dijkstra( int v0 )
{
    priority_queue  Q;  // 自定义的优先队列
    memset(dis,inf,sizeof(dis));  // 初始化dis为inf,避免和v0相连的点不能进入队列
    dis[v0] = 0;
    t.v = v0;
    t.date = 0;
    Q.push(t); // 先将顶点入队

    while ( !Q.empty() ) {
        if ( via[Q.top().v]==1 ) {  // 如果队列的点已经弹出过了,那么舍弃这个点
            Q.pop();
            continue ;
        }
        t = Q.top();
        Q.pop();
        int u = t.v;
        via[u] = 1;
        dis[u] = t.date; // 对于弹出来的点,就是已经做好了的点

        for ( i=1; i<=n; i++ ) {
            if ( via[i]==0 && a[u][i]dis[u]+a[u][i] ) {
                dis[i] = dis[u] + a[u][i]; // 更新最短路,并存入队列
                d.v = i;
                d.date = dis[i];
                Q.push(d);
            }
        }
    }
    cout << dis[n] << endl;
}

int main()
{
    cin >> m >> n;
    memset(a,inf,sizeof(a));
    memset(via,0,sizeof(via));
    for ( i=1; i<=n; i++ ) {
        a[i][i] = 0;
    }
    for ( i=1; i<=m; i++ ) {
        int x,y,z;
        cin >> x >> y >> z;
        if ( a[x][y]>z ) {
            a[x][y] = a[y][x] = z;
        }
    }

    dijkstra(1);

    return 0;
}

你可能感兴趣的:(专题四,最短路练习)