1:Bellman-Ford 算法
计算复杂度为 NM,只能计算单源,但是可以检测负值回环
操作流程:
1:选取所有边,以该边来进行松弛操作
2:循环n-1次
function [dist, pre]=bellmanford_ShortestPath(w,s)
%% initilization
n=size(w,1);
dist=ones(1,n)*inf;
pre=zeros(1,n)*NaN;
dist(s)=0;%% 进行松弛操作 进行n-1 次,每次遍历所有边
for k=1:n-1
for i=1:n
for j=1:n
if dist(j)>dist(i)+w(i,j)
dist(j)=dist(i)+w(i,j);
pre(j)=i;
end
end
end
end%% 回环确定
for i=1:n
for j=1:n
if w(i,j)~=inf
if (dist(j)>dist(i)+w(i,j))
error('negetive weight circut')
end
end
end
end
2:Floyd 算法
该算法最简单,但是可以计算多源路径,复杂度为 N*N*N
function [D,path]=Floyd_ShortestPath(w)
n=size(w,1);
D=w;
path=zeros(n,n);
for k=1:n
for i=1:n
for j=1:n
if D(i,j)>D(i,k)+D(k,j)
D(i,j)=D(i,k)+D(k,j);
path(i,j)=k;%% 也可以写作 path(i,j)=D(i,k);
end
end
end
end
end
Dijkstra算法
较为复杂的一种,计算复杂度为 N*N
操作流程如下:
1:初始化,见所有点分为两个集合 U和S, U为已选取的点,源点属于它,其余 点在S中
2:选取S中距离源点最近的点V,作为U下一个包含的对象
3:以V作为中间点,跟新所有S中的距离源点的最短路径
4:循环
function [dist]=Dijkstra_ShortestPath(w,s)
n=size(w,1);
dist=ones(1,n)*inf;
final=zeros(1,n);
%% initialization
dist=w(s,1:n);
final(s)=1;
dist(s)=0;
for i=1:n-1
min_result=inf;
index=find(final~=1);
temp=dist(index);
[ val,index_a]=min(temp);
index_a=index(index_a);
final(index_a)=1;
for i=1:n
if ( (final(i) ~=1) && (val+w(index_a,i)<dist(i)))
dist(i)=val+w(index_a,i);
end
end
end
end
路经的寻找(回溯法)
function print_floyd(path,s,t)
if path(s,t)>0
print_floyd(path,s,path(s,t));
print_floyd(path,path(s,t),t);
else
fprintf('->%s',num2str(t));
end