最短路总结:Dijkstra,SFPA,Bellman Ford判负环,Floyd
来源:互联网 发布:文华财经模拟软件 编辑:程序博客网 时间:2024/06/07 02:56
Dijkstra:(只能处理非负的)
贪心思想:
1、找到最短距离已经确定的顶点,从它出发更新相邻顶点的最短距离。
2、此后不需要再关心1中的“最短距离已确定的顶点”。
优先队列优化:
在队列中取出d值最小的结点x,然后从x出发更新所有的边的d值。
初始化:
first[u] 结点u的第一条边
next[i] 边i的下一条边
d -> INF
时间复杂度O(elogv)
#include <iostream>#include <cstring>#include <queue>#include <vector>#include <functional>using namespace std;//距离,边序号 typedef pair<int ,int> P;priority_queue<P, vector<P>, greater<P> >que;const int MAX_N = 10000, MAX_M = 10000;int d[MAX_N];struct E{int u, v, w;}e[MAX_M];int first[MAX_N], next[MAX_M];void Dijkstra(int s){//初始化,距离数组d,队列 memset(d, 0x3f, sizeof(d));d[s] = 0;que.push(P(d[s], s));while(que.size()){P x = que.top(); que.pop();//取出int u = x.second;if(x.first != d[u])//已经算过了,跳过 continue; for(int i = first[u]; i != -1; i = next[i])if(d[u] + e[i].w < d[e[i].v]){d[e[i].v] = d[u] + e[i].w;que.push(P(d[e[i].v], e[i].v));}}}int main(int argc, char *argv[]){memset(first, -1, sizeof(first));int n, m;scanf("%d%d", &n, &m);for(int i = 0; i < m; i++){scanf("%d%d%d", &e[i].u, &e[i].v, &e[i].w);next[i] = first[e[i].u];first[e[i].u] = i;}Dijkstra(e[0].u);printf("%d\n", d[5]);return 0;}
SPFA算法 负环最短路(用队列优化对Bellman Ford算法的优化):
时间复杂度:O(ke)。
初始化:
first[u] 结点u的第一条边
next[i] 边i的下一条边
d -> INF
bool inq[MAX_N];void SPFA(int s){//初始化距离d,队列,inq队列标志 queue<int> que;memset(d, 0x3f, sizeof(d));d[s] = 0;memset(inq, 0, sizeof(inq));que.push(s);while(que.size()){int u = que.front();que.pop();//清除标志 inq[u] = false;//对每一条邻边松弛操作 for(int i = first[u]; i != -1; i = next[i]) if(d[e[i].u] + e[i].w < d[e[i].v]){d[e[i].v] = d[e[i].u] + e[i].w;if(!inq[e[i].v]){inq[e[i].v] = true;que.push(e[i].v);}}}}
Bellman Ford算法判断是否存在负环:
若循环执行了n-1次,则存在负环。
注:d初始化为0即可
bool find_negative_loop(){memset(d, 0, sizeof(d));for(int i = 0; i < n; i++)for(int j = 0; j < m; j++){int u = e[j].u, v = e[j].v, w = e[j].w;if(d[u] + w < d[v]){d[v] = d[u] + w;if(i == n-1)return true;}}return false;}
Floyd-Warshall任意两点最短路算法:
动态规划的思想:
d[i][j] = min(d[i][j], d[i][k] + d[k][j]);
时间复杂度O(v^3)。
初始化:
d[][] -> INF
d[i][i] = 0;
d[u][v] = w;
void Floyd(){for(int k = 0; k < n; k++)for(int i = 0; i < n; i++)for(int j = 0; j < n; j++)d[i][j] = min(d[i][j], d[i][k] + d[k][j]);}
#include <iostream>#include <cstring>#include <queue>#include <vector>#include <functional>using namespace std;int n, m;//dist, utypedef pair<int, int> P;priority_queue<P, vector<P>, greater<P> >que; const int MAX_N = 10000, MAX_M = 10000;int d[MAX_N];//distantstruct E{int u, v, w;}e[MAX_M];int first[MAX_N], nexte[MAX_M];void Dijkstra(int s){memset(d, 0x3f, sizeof(d));d[s] = 0;que.push(P(d[s], s)); while(que.size()){P x = que.top(); que.pop();int u = x.second;//uif(x.first != d[u])//calc~edcontinue;for(int i = first[u]; i != -1; i = nexte[i])if(d[u] + e[i].w < d[e[i].v]){d[e[i].v] = d[u] + e[i].w;que.push(P(d[e[i].v], e[i].v));}}}bool inq[MAX_N];void SPFA(int s){//initqueue<int> que;memset(d, 0x3f, sizeof(d));d[s] = 0;memset(inq, 0, sizeof(inq));que.push(s);while(que.size()){int u = que.front(); que.pop();//clear flaginq[u] = false;//relaxfor(int i = first[u]; i != -1; i = nexte[i])if(d[e[i].u] + e[i].w < d[e[i].v]){d[e[i].v] = d[e[i].u] + e[i].w;if(!inq[e[i].v]){inq[e[i].v] = true;que.push(e[i].v);}}}}int dist[MAX_N][MAX_N];void Floyd(){for(int k = 0; k < n; k++)for(int i = 0; i < n; i++)for(int j = 0; j < n; j++)dist[i][j] = min(dist[i][j], dist[i][k] + dist[k][j]);}int main(){freopen("in.txt", "r", stdin);memset(first, -1, sizeof(first));//Floydmemset(dist, 0x3f, sizeof(dist));for(int i = 0; i < n; i++)dist[i][i] = 0;scanf("%d%d", &n, &m);for(int i = 0; i < m; i++){scanf("%d%d%d", &e[i].u, &e[i].v, &e[i].w);nexte[i] = first[e[i].u];first[e[i].u] = i;//Floyddist[e[i].u][e[i].v] = e[i].w;}Dijkstra(e[0].u);printf("%d to %d dist = %d\n", e[0].u, n-1, d[n-1]);SPFA(e[0].u);printf("%d to %d dist = %d\n", e[0].u, n-1, d[n-1]);Floyd();printf("%d to %d dist = %d\n", e[0].u, n-1, dist[e[0].u][n-1]);for(int i = 0; i < n; i++)for(int j = 0; j < n; j++){if(dist[i][j] == 0x3f3f3f3f)printf("INF");elseprintf("%3d", dist[i][j]);printf(j == n-1 ? "\n" : " ");}return 0;}/************************************************************************//* input:6 8 0 2 10 0 4 30 0 5 100 1 2 5 2 3 50 3 5 10 4 3 20 4 5 60 *//************************************************************************/
0 0
- 最短路总结:Dijkstra,SFPA,Bellman Ford判负环,Floyd
- 最短路 floyd dijkstra bellman-ford总结
- 最短路知识点总结(Dijkstra,Floyd,SPFA,Bellman-Ford)
- 最短路知识点总结(Dijkstra,Floyd,SPFA,Bellman-Ford)
- HDU-#2544 最短路(Dijkstra、Floyd、Bellman-Ford、SPFA)
- hdu 2544 最短路(Floyd-Warshal,Dijkstra,bellman-ford)
- 最短路(SPFA、Dijkstra、Floyd、Bellman-Ford)
- 最短路模板Dijkstra Bellman-Ford Floyd SPFA
- hdu-2544-最短路(Dijkstra + Dijkstra优先队列 + Bellman-ford + SPFA +Floyd) 纯模板题
- 最短路算法 Dijkstra Bellman-Ford SPFA
- 最短路算法 Dijkstra Bellman-ford 应用
- 最短路算法 :Bellman-ford算法 & Dijkstra算法 & floyd算法 & SPFA算法 详解
- 最短路算法 :Bellman-ford算法 & Dijkstra算法 & floyd算法 & SPFA算法 详解
- hdu1874(最短路:一道题学习Floyd,Dijkstra,Bellman-Ford,SPFA)
- HDU 2544 最短路(四种写法:Floyd、Dijkstra、Bellman-Ford、SPFA)
- 最短路算法 :Bellman-ford算法 & Dijkstra算法 & floyd算法 & SPFA算法 详解
- 最短路算法 :Bellman-ford算法 & Dijkstra算法 & floyd算法 & SPFA算法详解&BFS
- hdu-2544-最短路-(bellman-ford、dijkstra、floyd、SPFA算法)
- Android中对Log日志文件的分析
- Mule3用户手册:Mule ESB 3使用要点
- iOS系统GCD学习(1):介绍
- C++前向声明
- C# 多态性
- 最短路总结:Dijkstra,SFPA,Bellman Ford判负环,Floyd
- UIView 的 autoresizingMask 属性介绍
- Crawler4j在Eclipse中的配置
- 蓝桥杯入门训练 Fibonacci数列
- 一些关于交互的优秀解决方案
- draftsight+qgis+mapshaper+leftlet做web地图
- 黑马程序员_static 关键字
- 频谱和功率谱
- leetcode-Regular Expression Matching