当前位置:   article > 正文

Dijkstra算法(迪杰斯特拉算法)

Dijkstra算法(迪杰斯特拉算法)

迪杰斯特拉算法通常用在图的最短路径问题上

而迷宫的最短路径可以用BFS来做,虽然BFS不能用于带权值的迷宫,但是可以对BFS稍微改进,只需要把判断是否走过的数组改为最短路径的数组,在判断是否可走时判断是否比最短的小即可

Dijkstra步骤如下:

1,初始化一个graph二维数组来存储图的邻接表,一个dis一维数组来存储最短路径,一个check来存储是否走过

2,从起点开始,将起点的路径设置为0,也就是disp[起点] = 0

3,进入循环,每次寻找dis中最小的节点,然后遍历邻接表,如果邻接表的距离+该点的dis < dis[循环到的点],那么就迭代循环到的点,最后将最小的那个点check设置为true

  1. while(!end())
  2. {
  3. //寻找最小的点
  4. int min = max_num,min_num = max_num;
  5. for(int i = 1;i <= ::max;++i)
  6. {
  7. if(dis[i] < min_num && !check[i])
  8. {
  9. min = i;
  10. min_num = dis[i];
  11. }
  12. }
  13. //从邻接表中寻找这个点可到达的点,并迭代可到达的点的距离
  14. for(int i = 1;i <= ::max;++i)
  15. {
  16. if(graph[min][i] != max_num)
  17. {
  18. if(dis[i] > dis[min] + graph[min][i])
  19. {
  20. dis[i] = dis[min] + graph[min][i];//经过最小的那个点到达这个点的距离为dis[min] + graph[min][i]
  21. }
  22. }
  23. }
  24. //将最小的那个点标记
  25. check[min] = true;
  26. }

4,循环直到所有check都为true即可

也可以直接写一个函数判断

  1. //这里写了一个函数判断是否都被标记
  2. bool end()
  3. {
  4. for(int i = 1;i <= ::max;++i)
  5. {
  6. if(!check[i])
  7. {
  8. return false;
  9. }
  10. }
  11. return true;
  12. }

 c++代码如下

  1. #include <bits/stdc++.h>
  2. #define max_num 9999
  3. using namespace std;
  4. int graph[max_num][max_num];//邻接表,存储图
  5. int dis[max_num];//存储最短路径
  6. bool check[max_num];//存储是否被标记
  7. int max;//存储最大节点
  8. //这里写了一个函数判断是否都被标记
  9. bool end()
  10. {
  11. for(int i = 1;i <= ::max;++i)
  12. {
  13. if(!check[i])
  14. {
  15. return false;
  16. }
  17. }
  18. return true;
  19. }
  20. void dijkstra(int e)
  21. {
  22. while(!end())
  23. {
  24. //寻找最小的点
  25. int min = max_num,min_num = max_num;
  26. for(int i = 1;i <= ::max;++i)
  27. {
  28. if(dis[i] < min_num && !check[i])
  29. {
  30. min = i;
  31. min_num = dis[i];
  32. }
  33. }
  34. //从邻接表中寻找这个点可到达的点,并迭代可到达的点的距离
  35. for(int i = 1;i <= ::max;++i)
  36. {
  37. if(graph[min][i] != max_num)
  38. {
  39. if(dis[i] > dis[min] + graph[min][i])
  40. {
  41. dis[i] = dis[min] + graph[min][i];//经过最小的那个点到达这个点的距离为dis[min] + graph[min][i]
  42. }
  43. }
  44. }
  45. //将最小的那个点标记
  46. check[min] = true;
  47. }
  48. }
  49. int main()
  50. {
  51. //初始化,memset不可以用INT_MAX赋值,因为INT_MAX为无符号数最大值为1111111111111111,而memset会将其转换为有符号数的补码也就是-1
  52. memset(dis,max_num,sizeof(dis));
  53. memset(check, false,sizeof(check));
  54. memset(graph,max_num,sizeof(graph));
  55. int n;
  56. cin >> n >> ::max;
  57. int times = n;
  58. while(times--)
  59. {
  60. int x,y,z;
  61. cin >> x >> y >> z;
  62. graph[x][y] = z;
  63. graph[y][x] = z;
  64. }
  65. #if 0
  66. //输出邻接表
  67. for(int i = 0;i <= ::max;++i)
  68. {
  69. for(int j = 0;j <= ::max;++j)
  70. {
  71. printf("%5d ",graph[i][j]);
  72. }
  73. cout << endl;
  74. }
  75. #endif
  76. //起点启动
  77. int start;
  78. cin >> start;
  79. dis[start] = 0;
  80. dijkstra(start);
  81. //输出每个点到起点的最短路径
  82. for(int i = 1;i <= ::max;++i)
  83. {
  84. cout << i << " : " << dis[i] << endl;
  85. }
  86. }
  87. /*
  88. 10 7
  89. 1 3 2
  90. 1 2 5
  91. 2 4 9
  92. 3 4 3
  93. 3 6 2
  94. 4 6 4
  95. 4 5 8
  96. 5 6 9
  97. 5 7 3
  98. 6 2 7
  99. 1
  100. */

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/不正经/article/detail/707164
推荐阅读
相关标签
  

闽ICP备14008679号