C++ Bellman-ford邻接矩阵不检测负循环的单源最短路径
我曾尝试实现Bellman-ford单源最短路径的邻接矩阵,但它并没有检测到负循环中的一个顶点 同样的算法适用于边列表,但在邻接矩阵中给出了错误 这是图形的外观: 我的代码:C++ Bellman-ford邻接矩阵不检测负循环的单源最短路径,c++,c++11,shortest-path,bellman-ford,C++,C++11,Shortest Path,Bellman Ford,我曾尝试实现Bellman-ford单源最短路径的邻接矩阵,但它并没有检测到负循环中的一个顶点 同样的算法适用于边列表,但在邻接矩阵中给出了错误 这是图形的外观: 我的代码: #include <iostream> #include <climits> #include <vector> using namespace std; #define INF INT_MAX #define NINF INT_MIN void shortestpath(int
#include <iostream>
#include <climits>
#include <vector>
using namespace std;
#define INF INT_MAX
#define NINF INT_MIN
void shortestpath(int src, vector<vector<int>> &matrix){
int N = matrix.size();
vector<int> dist(N, INF);
vector<int> prev(N, 0);
dist[src] = 0;
for(int k = 0; k < N-1; k++){
for(int i = 0; i < N; i++){
for(int j = 0; j < N; j++){
if(dist[i] != INF && matrix[i][j] && dist[j] > (dist[i] + matrix[i][j]) ){
dist[j] = dist[i] + matrix[i][j];
prev[j] = i;
}
}
}
}
// for(int i = 0; i < N; i++)
// if(i != src)
// cout << src << " - " << i << "\t" << dist[i] << endl;
// cout << "\n\n";
// to check if -ve cycles exist or not
for(int k = 0; k < N-1; k++){
for(int i = 0; i < N; i++){
for(int j = 0; j < N; j++){
if(matrix[i][j] && dist[j] > (dist[i] + matrix[i][j]) ){
dist[j] = NINF;
prev[j] = -1;
}
}
}
}
for(int i = 0; i < N; i++)
if(i != src)
cout << src << " - " << i << "\t" << dist[i] << endl;
return ;
}
// Driver function
int main(){
int V = 8;
vector<vector<int>> matrix(V, vector<int>(V, 0));
matrix[0][1] = 1;
matrix[1][2] = 1;
matrix[2][4] = 1;
matrix[4][3] = -3;
matrix[3][2] = 1;
matrix[1][5] = 4;
matrix[1][6] = 4;
matrix[5][6] = 5;
matrix[6][7] = 4;
matrix[5][7] = 3;
shortestpath(0, matrix);
return 0;
}
在2->4->3有一个-ve循环,但我的代码在第二个循环中只检测到2和4,如果
dist[i]+matrix[i][j]
已经设置为INT\u MIN
并且matrix[i][j]
为负值,则dist[i]
可能通过整数溢出的方式显示未指定的行为。实际上,求和会变成一个大的正数,然后条件dist[j]>(dist[i]+matrix[i][j])
不成立,并且dist[j]
不会更新。谢谢@TedLyngmoThank@tedlynmo提供的信息,我已经进行了相应的编辑,欢迎!您尝试过什么样的调试?您是否使用了真正的调试器或尝试打印出函数中的值以查看出错的地方?后者通常足以调试小程序。对于(int k=0;k
我觉得这应该转到N-1(注意严格的小于那里)(更新:如果这解决了您的问题,请告诉我,我会在回答中写下它,以便它可以正确关闭)@TedLyngmo我试着打印出这些值,这就是为什么我知道负循环中某个顶点的值不会改变,但正如下面的答案中所提到的,这是由于在-ve无穷大中添加-ve数字的未指定行为,现在我可以看到,权重为-ve的顶点的值没有改变由于-ve无穷大的这种行为,在2'循环中的t值
0 -> 1 = 1
0 -> 2 = -2147483648
0 -> 3 = -3
0 -> 4 = -2147483648
0 -> 5 = 5
0 -> 6 = 5
0 -> 7 = 8