BFS 算法像是近视的小明的眼镜掉在了地上,小明肯定是先摸索离手比较近的位置,然后手慢慢向远方延伸,直至摸到眼镜,像是以小明为中心搜索圈不断扩大的过程。
通常用队列(先进先出,FIFO)实现
初始化队列Q;
Q = {起点s};标记s为已访问;
while(Q非空):
取Q队首元素u;u出队;
if u == 目标状态 {...}
所有与u相邻且未被访问的点进入队列;
标记u为已访问;
“一马当先”
下过象棋的人都知道,马只能走'日'字形(包括旋转90°的日),现在想象一下,给你一个n行m列网格棋盘, 棋盘的左下角有一匹马,请你计算至少需要几步可以将它移动到棋盘的右上角,若无法走到,则输出-1. 如n=1,m=2,则至少需要1步;若n=1,m=3,则输出-1。
首先我们直接按照上面的程序流程来进行代码实现。
代码一:
from collections import deque
n = 3
m = 5
def steps_count2():
'''
BFS算法求解,广度优先搜索算法
通常用队列(先进先出,FIFO)实现
初始化队列Q;
Q = {起点s};标记s为已访问;
while(Q非空):
取Q队首元素u;u出队;
if u == 目标状态 {...}
所有与u相邻且未被访问的点进入队列;
标记u为已访问;
:return:
'''
global m,n
dx = [-1, -2, -2, -1, +1, +2, +2, +1]
dy = [+2, +1, -1, -2, -2, -1, +1, +2]
v = {(x, y): False for x in range(0, n + 1) for y in range(0, m + 1)}
v[(0, 0)] = True
q = deque([(0, 0, 0)])
while len(q) > 0:
p = q.popleft()
for i in range(8):
x = p[0] + dx[i]
y = p[1] + dy[i]
if x < 0 or x > n or y < 0 or y > m:
continue
if v[(x, y)]:
continue
v[(x, y)] = True
q.append((x, y, p[2] + 1))
if x == n and y == m:
return p[2] + 1
return -1
元素定义
流程分析
代码二:
n = 3
m = 5
def steps_count4():
global m, n
dx = [+2, +1, -1, -2, -2, -1, +1, +2]
dy = [-1, -2, -2, -1, +1, +2, +2, +1]
temp = [set(), set([(0, 0)]), set()]
t = 1
f = True
while f:
f = False
for loc in temp[1]:
for i in range(8):
x = loc[0] + dx[i]
y = loc[1] + dy[i]
if (x,y) == (m, n):
return t
elif x >= 0 and y >= 0 and x <= m and y <= n and not ((x,y) in temp[0] or (x,y) in temp[1] or (x,y) in temp[2]):
temp[2].add((x,y))
f = True
t += 1
del temp[0]
temp.append(set())
return -1
元素定义
流程解析