zoukankan      html  css  js  c++  java
  • 【C/C++】Dijkstra算法的简洁实现

     

     Dijkstra的实现有很多种,下面给出一种较为简洁和高效的实现,可以作为模板快速使用。

      1. 使用邻接表存储图;

      2. 使用标准STL的vector存储每个点的所有邻接边;

      3. 使用pair记录当前搜索的点,pair<int,int>对:

        first记录最小距离,用以在优先队列中实现类似'最小堆优化';

        second记录该最小距离对应的点;

      4. 使用priority_queue实现优化;(附使用方法)

      5. 一个细节:这是盲目检索,中途若D[i] < p.first,说明队列里的该点已经到达了,这个pair已经无效,直接continue;

     

      实现:

     1 #include<bits/stdc++.h> 
     2 #define INF 100000005
     3 #define MAX 100006 
     4 using namespace std;
     5 
     6 typedef pair<int,int> P;
     7 
     8 struct edge{
     9     int to;
    10     int cost;
    11     edge(int t,int c):to(t),cost(c){
    12     }
    13 };
    14 
    15 const int N = 100006;
    16 vector<edge> g[N];
    17 int D[N]; //距离 
    18 int n,m; //n个点 m条边 
    19 
    20 void Dijkstra(int s){
    21     priority_queue<P,vector<P>,greater<P> > que; //小端优先队列 
    22     fill(D,D+MAX,INF);//注意必须初始化为最大
    23     D[s] = 0;
    24     que.push(P(0,s));
    25     while(!que.empty()){
    26         P p = que.top();
    27         que.pop();
    28         int v = p.second;
    29         if(D[v] < p.first) continue; //说明该点无需重复
    30         for(int i = 0;i<g[v].size();i++) {
    31             //遍历所有后续边 
    32             edge e = g[v][i];
    33             int to = e.to;
    34             int cost = e.cost;
    35             if(D[to] > D[v] + cost){
    36                 D[to] = D[v] + cost;
    37                 que.push(P(D[to],to));
    38             }
    39         }
    40     }
    41 }
    42 
    43 int main(){
    44     cin>>n>>m;
    45     int a,b,d;
    46     //Vector<edge> g[MAX]的初始化
    47     for(int i = 0;i<MAX;i++) {
    48         g[i].clear();
    49     }
    50     //距离D的初始化
    51     //fill(D,D+MAX,INF) ;//等Dijkstra时再初始化也行 
    52     for(int i = 0;i<m;i++){
    53         cin>>a>>b>>d;
    54         g[a].push_back(edge(b,d));
    55         g[b].push_back(edge(a,d));
    56     }
    57     int s,t;//起点 终点 
    58     s = 1;
    59     t = n;
    60     Dijkstra(s);
    61     cout<<D[n]<<endl;
    62     return 0;
    63 }

       【Appendix】

      priority_queue的使用方法:

    • 对于基本数据:
      •  priority_queue<int> q;
      •  priority_queue<int,vector<int>,less<int> > q; //默认,less可以省
      •  这创建的是‘大 ’优先队列,大的在top
      •  取:q.top();
      •  出:q.pop();
      •  放:q.push(int);

     

    •  创建‘小 ’优先队列:
      •  priority_queue<int,vector<int>,greater<int> > q;

     

    •  对于结构体数据:
      •  1. 结构体运算符重载

         bool operator < (const struct1,const struct1) const{
           return ?;
          }

      • 2. 定义cmp函数,做参数传入,更加灵活

          bool cmp(struct1,struct2){
             return ?;
          }
          priority_queue<struct1,vector<struct2>,cmp> q;

      

     

     

     

  • 相关阅读:
    视频直播:Windows中各类画面源的截取和合成方法总结
    短视频技术详解:Android端的短视频开发技术
    视频直播关键技术:流畅、拥塞和延时追赶
    视频直播技术详解:直播的推流调度
    直播技术:从性能参数到业务大数据,浅谈直播CDN服务监控
    音视频通话:小议音频处理与压缩技术
    pip命令报错“no perl script found in input”
    python常见面试题讲解(三)明明的随机数
    如何使用photoshop修改图片的像素大小(分辨率)
    VMware Workstation如何修改弹出释放快捷键
  • 原文地址:https://www.cnblogs.com/duye/p/9537918.html
Copyright © 2011-2022 走看看