• Dijkstra求单源最短路


    849. Dijkstra求最短路 I

    给定一个 n

    个点 m

    条边的有向图,图中可能存在重边和自环,所有边权均为正值。

    请你求出 1

    号点到 n 号点的最短距离,如果无法从 1 号点走到 n 号点,则输出 −1

    输入格式

    第一行包含整数 n

    和 m

    接下来 m

    行每行包含三个整数 x,y,z,表示存在一条从点 x 到点 y 的有向边,边长为 z

    输出格式

    输出一个整数,表示 1

    号点到 n

    号点的最短距离。

    如果路径不存在,则输出 −1

    数据范围

    1≤n≤500

    ,
    1≤m≤105

    ,
    图中涉及边长均不超过10000。

    输入样例:

    1. 3 3
    2. 1 2 2
    3. 2 3 1
    4. 1 3 4

    输出样例:

    3
    

     * Dijkstra 算法:单源最短路径问题;
     * 将源点的距离设置为0,接下来Nv轮循环,找出还未被加入集合且离源点最近的顶点,
     * 如果时找到的这个顶点与源点有路相通,则这个顶点与源点的距离一定是这个顶点与源点之间
     * 的距离最短的,不可能从源点途径另外一个顶点到达此顶点的距离更小(如果有,那么一定还有
     * 与此点未连通且离源点的距离更小的点,并且是正权图,所以与前面的话(找出还未被加入集合
     * 且离源点最近的顶点)矛盾),所以此算法正确;

    1. /**
    2. * Dijkstra 算法:单源最短路径问题;
    3. * 将源点的距离设置为0,接下来Nv轮循环,找出还未被加入集合且离源点最近的顶点,
    4. * 如果时找到的这个顶点与源点有路相通,则这个顶点与源点的距离一定是这个顶点与源点之间
    5. * 的距离最短的,不可能从源点途径另外一个顶点到达此顶点的距离更小(如果有,那么一定还有
    6. * 与此点未连通且离源点的距离更小的点,并且是正权图,所以与前面的话(找出还未被加入集合
    7. * 且离源点最近的顶点)矛盾),所以此算法正确;
    8. */
    9. #include <iostream>
    10. #include <algorithm>
    11. using namespace std;
    12. const int maxn = 510,INF=1e9;
    13. int G[maxn][maxn]; //邻接矩阵
    14. int d[maxn]; //距离数组
    15. bool hs[maxn]; //记录顶点是否被选择
    16. int Nv,Ne; //顶点数,边数
    17. void Read() //读入数据
    18. {
    19. fill(*G,*G+maxn*maxn,INF);
    20. cin >> Nv >> Ne;
    21. for(int i=0;i<Ne;++i)
    22. {
    23. int u,v,w;
    24. cin >> u >> v >> w;
    25. G[u][v]=min(G[u][v],w); //存在重边,选择权值最小的边即可
    26. }
    27. }
    28. int Dijkstra(int st) //各点到st顶点的最短距离
    29. {
    30. fill(d,d+maxn,INF);
    31. d[st]=0; //源点的距离为0
    32. for(int i=0;i<Nv;++i)
    33. {
    34. int u=-1,MIN=INF;
    35. for(int j=1;j<=Nv;++j)
    36. if(hs[j]==0 && d[j]<MIN)
    37. {
    38. MIN=d[j];
    39. u=j;
    40. }
    41. if(u==-1) //如果u等于-1,说明图不连通
    42. return -1;
    43. hs[u]=1;
    44. for(int v=1;v<=Nv;++v)
    45. if(G[u][v]!=INF && hs[v]==0 && d[u]+G[u][v]<d[v]) //u,v有边且v还未被选中
    46. d[v]=d[u]+G[u][v]; //且从源点到v途径u能使源点到v的距离变小
    47. }
    48. return d[Nv];
    49. }
    50. int main()
    51. {
    52. Read();
    53. cout << Dijkstra(1) << endl;
    54. return 0;
    55. }

    850. Dijkstra求最短路 II

    给定一个 n

    个点 m

    条边的有向图,图中可能存在重边和自环,所有边权均为非负值。

    请你求出 1

    号点到 n 号点的最短距离,如果无法从 1 号点走到 n 号点,则输出 −1

    输入格式

    第一行包含整数 n

    和 m

    接下来 m

    行每行包含三个整数 x,y,z,表示存在一条从点 x 到点 y 的有向边,边长为 z

    输出格式

    输出一个整数,表示 1

    号点到 n

    号点的最短距离。

    如果路径不存在,则输出 −1

    数据范围

    1≤n,m≤1.5×105

    ,
    图中涉及边长均不小于 0,且不超过 10000。
    数据保证:如果最短路存在,则最短路的长度不超过 109

    输入样例:

    1. 3 3
    2. 1 2 2
    3. 2 3 1
    4. 1 3 4

    输出样例:

    3
    

     * Dijkstra 算法:单源最短路径问题;
     * 将源点的距离设置为0,接下来Nv轮循环,找出还未被加入集合且离源点最近的顶点,
     * 如果时找到的这个顶点与源点有路相通,则这个顶点与源点的距离一定是这个顶点与源点之间
     * 的距离最短的,不可能从源点途径另外一个顶点到达此顶点的距离更小(如果有,那么一定还有
     * 与此点未连通且离源点的距离更小的点,并且是正权图,所以与前面的话(找出还未被加入集合
     * 且离源点最近的顶点)矛盾),所以此算法正确;
     *
     * 堆优化版的 Dijkstra 算法和朴素版的算法思想一样,只不过求解还未被加入集合且离源点
     * 最近的顶点时,用最小堆来求,这样算法时间复杂度可以下降为 O(n*logn);

    1. /**
    2. * Dijkstra 算法:单源最短路径问题;
    3. * 将源点的距离设置为0,接下来Nv轮循环,找出还未被加入集合且离源点最近的顶点,
    4. * 如果时找到的这个顶点与源点有路相通,则这个顶点与源点的距离一定是这个顶点与源点之间
    5. * 的距离最短的,不可能从源点途径另外一个顶点到达此顶点的距离更小(如果有,那么一定还有
    6. * 与此点未连通且离源点的距离更小的点,并且是正权图,所以与前面的话(找出还未被加入集合
    7. * 且离源点最近的顶点)矛盾),所以此算法正确;
    8. *
    9. * 堆优化版的 Dijkstra 算法和朴素版的算法思想一样,只不过求解还未被加入集合且离源点
    10. * 最近的顶点时,用最小堆来求,这样算法时间复杂度可以下降为 O(n*logn);
    11. */
    12. #include <iostream>
    13. #include <algorithm>
    14. #include <queue>
    15. #include <vector>
    16. using namespace std;
    17. struct ENode
    18. {
    19. int v,w;
    20. };
    21. typedef pair<int,int> PII;
    22. const int maxn = 1.5e5+10 ,INF=1e9;
    23. vector<ENode> Adj[maxn]; //邻接表int d[maxn];
    24. int d[maxn]; //距离数组
    25. bool hs[maxn]; //记录顶点是否被选择
    26. int Nv,Ne; //顶点数,边数
    27. void Read() //读入数据
    28. {
    29. cin >> Nv >> Ne;
    30. for(int i=0;i<Ne;++i)
    31. {
    32. int u,v,w;
    33. cin >> u >> v >> w;
    34. Adj[u].push_back({v,w});
    35. }
    36. }
    37. void Dijkstra(int st) //各点到st顶点的最短距离
    38. {
    39. //priority_queue 默认为小根堆,但是为什么非要加后面两句呢?
    40. //priority_queue<PII> q 就表示最小堆,或许是pair的缘故吧;
    41. //知道缘故了,priority_queue 默认为大根堆;
    42. priority_queue<PII,vector<PII>,greater<PII> > q;
    43. q.push({0,st});
    44. fill(d,d+maxn,INF);
    45. d[st]=0;
    46. while(q.size())
    47. {
    48. PII top=q.top();
    49. q.pop();
    50. int u=top.second;
    51. if(hs[u])
    52. continue;
    53. hs[u]=1;
    54. for(int i=0;i<Adj[u].size();++i)
    55. {
    56. int v=Adj[u][i].v,w=Adj[u][i].w;
    57. if(hs[v]==0 && d[u]+w<d[v])
    58. {
    59. d[v]=d[u]+w;
    60. q.push({d[v],v});
    61. }
    62. }
    63. }
    64. }
    65. int main()
    66. {
    67. Read();
    68. Dijkstra(1);
    69. if(d[Nv] == INF)
    70. cout << -1 << endl;
    71. else
    72. cout << d[Nv] << endl;
    73. return 0;
    74. }

  • 相关阅读:
    Leetcode.337 打家劫舍 III
    技术分享 | 使用 Zabbix + Grafana 搭建服务器监控系统
    对图片进行base64编解码
    项目中升级mysql遇到的若干问题
    React Hooks学习笔记
    用友U8 CRM客户关系管理任意文件上传漏洞复现【附POC】
    板块一 Servlet编程:第七节 ServletContext对象全解与Servlet三大域对象总结 来自【汤米尼克的JAVAEE全套教程专栏】
    MySQL JDBC编程
    git的常见命令介绍
    五十二、BBS项目
  • 原文地址:https://blog.csdn.net/qq_51825761/article/details/126750752