最短路算法汇总
优先队列优化的Dijkstra:
1 #include <bits/stdc++.h> 2 3 using namespace std; 4 5 const int MAXN = 5e5 + 5, inf = 0x3f3f3f3f; 6 7 struct point { 8 int id, dis; 9 }; 10 11 struct cmp { 12 bool operator ()(const point &x, const point &y) { 13 return x.dis > y.dis; 14 } 15 }; 16 17 struct edge { 18 int to, nxt, val; 19 } edges[MAXN]; 20 21 priority_queue <point, vector<point>, cmp> heap; 22 int head[MAXN], dist[MAXN], cnt = 0; 23 bool vis[MAXN]; 24 25 void addEdge(int from, int to, int val) { 26 edges[cnt].to = to; edges[cnt].nxt = head[from]; edges[cnt].val = val; 27 head[from] = cnt++; 28 } 29 30 void dijkstra(int s) { 31 memset(dist, 0x3f, sizeof(dist)); 32 dist[s] = 0; 33 point tmp; 34 tmp.id = s; tmp.dis = 0; 35 heap.push(tmp); 36 while(!heap.empty()) { 37 while(!heap.empty() && vis[heap.top().id]) heap.pop(); 38 if(heap.empty()) break; 39 tmp = heap.top(); heap.pop(); 40 vis[tmp.id] = true; 41 for(int i = head[tmp.id]; i != -1; i = edges[i].nxt) 42 if(dist[tmp.id] + edges[i].val < dist[edges[i].to]) { 43 dist[edges[i].to] = dist[tmp.id] + edges[i].val; 44 point ntmp; 45 ntmp.id = edges[i].to; ntmp.dis = dist[edges[i].to]; 46 heap.push(ntmp); 47 } 48 } 49 } 50 51 52 int main() { 53 ios::sync_with_stdio(false); 54 memset(head, 0xff, sizeof(head)); 55 int n, m, u, v, w, s; 56 cin >> n >> m >> s; 57 for(int i = 0; i < m; i++) { 58 cin >> u >> v >> w; 59 addEdge(u, v, w); 60 } 61 dijkstra(s); 62 for(int i = 1; i <= n; i++) 63 cout << (dist[i] == inf ? 0x7fffffff : dist[i]) << " "; 64 cout << endl; 65 return 0; 66 }
线段树优化的Dijkstra:
1 #include <bits/stdc++.h> 2 3 using namespace std; 4 5 const int MAXN = 1e5 + 5, inf = 0x3f3f3f3f; 6 7 int st[MAXN << 3], head[MAXN], dist[MAXN], ans[MAXN], n, m, cnt = 0; 8 bool vis[MAXN]; 9 10 struct edge { 11 int to, nxt, val; 12 } edges[MAXN << 1]; 13 14 void addedge(int from, int to, int val) { 15 edges[cnt].to = to, edges[cnt].val = val; 16 edges[cnt].nxt = head[from]; head[from] = cnt++; 17 } 18 19 void pushup(int x) { 20 st[x] = dist[st[x << 1]] < dist[st[x << 1 | 1]] ? st[x << 1] : st[x << 1 | 1]; 21 } 22 23 void build(int x, int l, int r) { 24 if(l < r) { 25 int mid = (l + r) >> 1; 26 build(x << 1, l, mid); 27 build(x << 1 | 1, mid + 1, r); 28 pushup(x); 29 } else st[x] = l; 30 } 31 32 void updata(int x, int l, int r, int q) { 33 if(l != r) { 34 int mid = (l + r) >> 1; 35 if(q <= mid) updata(x << 1, l, mid, q); 36 else updata(x << 1 | 1, mid + 1, r, q); 37 pushup(x); 38 } 39 } 40 41 void dijkstra(int s) { 42 ans[s] = dist[s] = 0; 43 build(1, 1, n); 44 while(dist[st[1]] < inf) { 45 int v = st[1]; vis[v] = 1; 46 for(int i = head[v]; i != -1; i = edges[i].nxt) if(!vis[edges[i].to]) { 47 dist[edges[i].to] = min(dist[edges[i].to], dist[v] + edges[i].val); 48 updata(1, 1, n, edges[i].to); 49 } 50 ans[v] = dist[v]; dist[v] = inf; 51 updata(1, 1, n, v); 52 } 53 } 54 55 int main() { 56 ios::sync_with_stdio(false); 57 memset(dist, 0x3f, sizeof(dist)); 58 memset(head, 0xff, sizeof(head)); 59 memset(ans, 0x3f, sizeof(ans)); 60 int u, v, w, s; 61 cin >> n >> m >> s; 62 for(int i = 0; i < m; i++) { 63 cin >> u >> v >> w; 64 addedge(u, v, w); 65 } 66 dijkstra(s); 67 for(int i = 1; i <= n; i++) cout << ans[i] << " "; 68 cout << endl; 69 return 0; 70 }

浙公网安备 33010602011771号