算法(最短路径dijkstra算法实现)

示例题目

算法导论--单源最短路径问题(Dijkstra算法)-CSDN博客

我的思路是参考这篇文章的

题目为:

先构建邻接矩阵

#define INFINITE 10000;   
#define vexCounts 6  //顶点数量
int vextex[] = { 0,1,2,3,4,5};
void AdjMatrix(int adjMat[][vexCounts])  //邻接矩阵表示法
{
    for (int i = 0; i < vexCounts; i++)   //初始化邻接矩阵
        for (int j = 0; j < vexCounts; j++)
        {
           adjMat[i][j] = INFINITE;
        }
    adjMat[0][1] = 50; adjMat[0][2] = 10; adjMat[0][4] = 45;
    adjMat[1][2] = 15; adjMat[1][4] = 10; 
    adjMat[2][0] = 20; adjMat[2][3] = 15; 
    adjMat[3][1] = 20; adjMat[3][4] = 35; adjMat[3][5] = 3;
    adjMat[4][3] = 30; 
}

注意:这块的INFINITE,我并没有设置成那篇文章里面的,好像那样的话,就成-1了,在我这里是不合适的

实现dijkstra算法

一、初始化
1.1设置三个数组
int dist[vexCounts]; //存储源点到个顶点的最短距离  ,默认无穷大
    bool Flag[vexCounts];  //记录顶点是否已包括在最短路径里||是否处理过该点
    int path[vexCounts];    //记录前驱,默认为顶点
    int maxInt=INFINITE; //
1.2初始化这三个数组

在给出源点(这里假设是0,也就是对应图中的'A')

 //1.初始化各顶点距离,起点到各点距离
    for(int i=0;i<vexCounts;i++){
       
         Flag[i]=false;  //
         dist[i]=graph[src][i];
         if(dist[i]<maxInt){
            path[i]=src;
         } else {
            path[i]=-1;
         }
    }
    Flag[src]=true; //
    dist[src]=0;  //源点到自身距离为0

先给Flag[]数组里面全都=false,说明这几个点都没有加入来着,也就是没有考虑。然后在距离矩阵dist[]里面,初始化成源点到各个点的直接距离(注:在构建邻接矩阵时,即使图中源点到某点没有直接路径,这里将其设为了INFINITE(100))。

然后就是path[]数组,记录前驱的,这里其实可以直接写作path[i]=src的,因为本来就是源点到每个点的直接距离。

初始化结束后,因为已经考虑了源点,所以Flag[src]=true;

1.3初始化结束,进入主循环
首先肯定是一个大循环
//对剩下的vexCount-1个顶点进行遍历
    for(int i=1;i<vexCounts;i++){
    ...
}
在这个大循环里,先找到dist[]数组中最小的顶点,将它进行考虑

这个过程是会进行vexCounts-1次,每次都选剩下没有考虑的点中,dist[]值最小的

 int v;
    /*
        初始化结束,开始主循环
    */
    //对剩下的vexCount-1个顶点进行遍历
    for(int i=1;i<vexCounts;i++){
        int min=maxInt;
        //2.1选出当前表中权重和最短的点,并且是没有进去过的
        for(int j=1;j<vexCounts;j++){
            if(Flag[j]!=1&&dist[j]<min){
                v=j;
                min=dist[j];
               
            }
        }
         cout<<"in dist[] shortest:"<<v<<endl;
        Flag[v]=true;
选出该点以后

就要重新判断dist[]了,同时记得更新path[];

 for(int i=0;i<vexCounts;i++){
            if(Flag[i]!=1&&dist[v]+graph[v][i]<dist[i]){   //源点到当前点的值+当前点到下一个点的值 < 源点到下一个点的值
                dist[i]=dist[v]+graph[v][i];
                path[i]=v;  //更新前驱点
            }
        }
测试如下
int main(){
    int adjMat[6][6];
    AdjMatrix(adjMat);
    for(int i=0;i<6;i++){
        for(int j=0;j<6;j++) {
            cout<<adjMat[i][j]<<" ";
        }
        cout<<'\n';
    }
    ShortestPath_DIJ(adjMat, 0);


    return 0;
}

可以看出结果是对的。当然也可以根据那三个数组,写出更详细的输出结果,我这里就懒得写了。

感觉写的思路还是蛮清楚的。如果有什么没有理解的,也可以评论区提出哦。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值