MATLAB 广度优先搜索BFS、深度优先搜索DFS


如此经典的算法竟一直没有单独的实现过,真是遗憾啊。

广度优先搜索在过去实现的二值图像连通区域标记和prim最小生成树算法时已经无意识的用到了,深度优先搜索倒是没用过。

这次单独的将两个算法实现出来,因为算法本身和图像没什么关系,所以更纯粹些。

广度优先搜索是从某一节点开始,搜索与其线连接的所有节点,按照广度方向像外扩展,直到不重复遍历所有节点。

深度优先搜索是从某一节点开始,沿着其搜索到的第一个节点不断深入下去,当无法再深入的时候,回溯节点,然后再在回溯中的某一节点开始沿另一个方向深度搜索,直到不重复的遍历所有节点。

广度优先搜索用的是队列作为临时节点存放处;深度优先搜索可以递归实现(算法导论就是用递归实现的伪代码),不过我这里是用栈作为临时节点存放处。

感觉也没什么好介绍的了,抄算法导论上的介绍也没什么意思,所有的内容都是书上的,真正学东西还是要看书。

下面是运行结果:

原连通图:

广度优先搜索:

深度优先搜索:

matlab代码如下,其中的画图函数netplot.m。

BFS.m

 1 clear all;close all;clc  2 %初始化邻接压缩表  3 b=[1 2;1 3;1 4;2 4;  4    2 5;3 6;4 6;4 7];  5 
 6 m=max(b(:));                %压缩表中最大值就是邻接矩阵的宽与高  7 A=compresstable2matrix(b);  %从邻接压缩表构造图的矩阵表示  8 netplot(A,1)                %形象表示  9 
10 head=1;             %队列头 11 tail=1;             %队列尾,开始队列为空,tail==head 12 queue(head)=1;      %向头中加入图第一个节点 13 head=head+1;        %队列扩展 14 
15 flag=1;             %标记某个节点是否访问过了 16 re=[];              %最终结果 17 while tail~=head    %判断队列是否为空 18     i=queue(tail);  %取队尾节点 19     for j=1:m 20         if A(i,j)==1 && isempty(find(flag==j,1))    %如果节点相连并且没有访问过 21             queue(head)=j;                          %新节点入列 22             head=head+1;                            %扩展队列 23             flag=[flag j];                          %对新节点进行标记 24             re=[re;i j];                            %将边存入结果 25  end 26  end 27     tail=tail+1; 28 end 29 
30 A=compresstable2matrix(re); 31 figure; 32 netplot(A,1)

DFS.m

 1 clear all;close all;clc  2 %初始化邻接压缩表  3 b=[1 2;1 3;1 4;2 4;  4    2 5;3 6;4 6;4 7];  5 
 6 m=max(b(:));                %压缩表中最大值就是邻接矩阵的宽与高  7 A=compresstable2matrix(b);  %从邻接压缩表构造图的矩阵表示  8 netplot(A,1)                %形象表示  9 
10 top=1;                  %堆栈顶 11 stack(top)=1;           %将第一个节点入栈 12 
13 flag=1;                 %标记某个节点是否访问过了 14 re=[];                  %最终结果 15 while top~=0            %判断堆栈是否为空 16     pre_len=length(stack);    %搜寻下一个节点前的堆栈长度 17     i=stack(top);             %取堆栈顶节点 18     for j=1:m 19         if A(i,j)==1 && isempty(find(flag==j,1))    %如果节点相连并且没有访问过 20             top=top+1;                          %扩展堆栈 21             stack(top)=j;                       %新节点入栈 22             flag=[flag j];                      %对新节点进行标记 23             re=[re;i j];                        %将边存入结果 24             break; 25  end 26  end 27     if length(stack)==pre_len   %如果堆栈长度没有增加,则节点开始出栈 28         stack(top)=[]; 29         top=top-1; 30  end 31 end 32 
33 A=compresstable2matrix(re); 34 figure; 35 netplot(A,1)

compresstable2matrix.m

 1 function A=compresstable2matrix(b)  2     [n ~]=size(b);  3     m=max(b(:));  4     A=zeros(m,m);  5 
 6     for i=1:n  7         A(b(i,1),b(i,2))=1;  8         A(b(i,2),b(i,1))=1;  9  end 10 
11 end

 


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM