宽度优先搜索BFS
~工作方式:
从根节点开始,由里向外,逐层遍历所有节点——它每次总是扩展深度最浅的节点。
~缺点:在树的层次较深&子节点数较多的情况下,消耗内存十分严重。
~适用情况:节点的子节点数量不多,并且树的层次不会太深的情况。
~简单举例:BFS方法,从根节点1开始,下图遍历顺序是:1,2,3,4,5,6
优先访问深度最浅的节点,故,老节点总是优先于新节点被访问,因此,我们可以使用队列来管理节点。
BFS算法的工作原理如下:
1.将根节点放入队列
2.重复以下,直到队列为空
{
2.1 取出队列头的点
2.2 找出与该点相邻并没有被访问的节点,标记后依次放入队列
}
图可以采用二维数组或者邻接表来保存
下面,我将用图来展示BFS算法的工作过程:
1.将起始节点1放入队列,进行标记
2.从队列取出头节点1,找到与该节点邻接的节点,依次放入队列,标记为已访问
3.取出队列头节点2,找到与2节点邻接的节点1,5,6。节点1已被访问,将节点5,6依次放入队列,标记为已访问
直到队列为空,后面操作重复,不再赘述。
以下用两种方式实现BFS算法:
1.队列的方式
# -*- coding: utf-8 -*-
#BFS算法的队列实现
from Queue import Queue
from Stack import Stack
from simplegraph import *
def BFS(G,v,goal,came_from):#G为导入的图;v为起始节点;goal为目标节点;
frontier=Queue()
frontier.enqueue(v)
came_from[v]=None
visited={
}
while not frontier.is_empty():#队列不为空
v=frontier.dequeue()#将节点v取出队列
if visited.get(v)==None:#判断节点v是否被访问过
if v==goal:
return v
else:
visited[v]=True#节点v被访问
for w in G.adjacentEdges(v):#依次取节点v的相邻节点w
frontier.enqueue(w)#将v相邻节点放入队列
came_from[w]=v
return None
def main():
came_from = {
}
start = '1'
goal = '12'
found = BFS(G1,start,goal,came_from)
print