Bellman ford算法求最短路c++
创始人
2025-05-29 01:36:07

适用

bellman-ford算法适用于有负边,且最短路径有边数限制的题目。
如果没有边数的限制并且有负边我们一般用spfa算法

讲解

其实和普通版的dijkstra差不多,略微有几处不同的地方。

  • 1,我们每次能遍历到所有节点就行了,所以就用结构体存储就可以了,当然你用别的也是可以的。
  • 2,在函数中第一次遍历,遍历多少次就代表最后有多少条边。限制变数的条件在这里实现。
  • 3,这里有个last数组,就是备份上一次的,要不然更新的时候容易出现串联,就是因为每次要遍历所有的节点,每次要更新一条边,举个例子吧。
    bellmanford.png
    假如说现在在j的for循环中,有一次更新了2的dist,但是我们我们在下一次更新3的时候我们不应该用2的w1权重,而是应该用2的上次的正无穷权重,因为一个i循环每个节点只能向外伸展一个节点。
  • 4,然后就是普通的更新了,a到b有一条边,看a能不能把b更新了。
  • 5,最后就是输出的时候,为什么要用dist[n] > 0x3f3f3f3f / 2呢,因为这是负权边,有可能倒数第二个节点到最后一个节点是个负权的,然后就把最后一个节点给更新了。图示…
    bellmanford2.png
  • 6,因为函数中要用到m,所以输入的时候不能用while(m--)

流程

bellmanford3.png
来源AcWing

源码

#include using namespace std;const int N = 510, M = 10010;int n, m, k;
int dist[N];
int last[N];struct Edges
{int a, b, w;
}edges[M];void bellman_ford()
{memset(dist, 0x3f, sizeof dist);dist[1] = 0;for (int i = 0; i < k; i ++){memcpy(last, dist, sizeof dist);for (int j = 0; j < m; j ++ ){dist[edges[j].b] = min(dist[edges[j].b], dist[edges[j].a] + edges[j].w);}}	
}int main()
{cin >> n >> m >> k;for (int i = 0; i < m; i ++ ){int a, b, c;cin >> a >> b >> c;edges[i] = {a, b, c};}bellman_ford();if (dist[n] > 0x3f3f3f3f / 2) cout << "impossible" << "\n";else cout << dist[n] << "\n";
}

相关内容

热门资讯

“三月三”活动在小沧畲族乡举行... 大型歌舞《锦绣中华·石榴籽一家亲》。  4月19日,第三届“三月三”连马民族文化活动暨民族趣味运动会...
预售28.98万起!奥迪E7X... (来源:车联新生态)5月8日晚,上汽奥迪AUDI品牌全新车型——奥迪E7X正式开启预售。新车共推出4...
曾被忽视的历史铁证,中方立碑定... (来源:时报新征途)  中方又一次用实际行动,守护历史正义、明确主权立场。据中国驻埃及大使馆官方消息...
两条熟料生产线(2000t/d... (来源:水泥网APP)5月7日,贵州省工信厅发布“关于贵州博宏实业有限责任公司水泥分公司日产2000...
宁夏银川一外卖员用小区灭火器帮... 5月8日,宁夏银川一名外卖小哥告诉记者,他借用灭火器灭火被物业人员要求支付50元费用。外卖小哥称,6...