算法宗门---广度有优先搜索BFS

广度优先搜索(BFS,Breadth-First Search)

一、BFS 的 "生活化故事":像找迷宫出口一样 "层层扩散"

你可以把 BFS 想象成 "小时候玩迷宫的最稳妥办法":假设你站在迷宫的起点,想找到出口,但你分不清哪条路是对的。这时你不会一头扎进某条路死磕(那是深度优先搜索 DFS),而是先把离你一步之遥的所有路口 都标记出来(这些是 "第一层");然后从这些第一层路口出发,再把离它们一步之遥、且没被标记过的路口 标记出来("第二层");以此类推,直到某一层的人喊 "我找到出口了!"------ 这就是 BFS 的核心逻辑:层层递进、地毯式搜索

从学术角度说,BFS 的雏形最早出现在 19 世纪数学家康托尔、若尔当对图结构的研究中,后来被系统应用到计算机领域。它没有 "一个人灵光一闪发明" 的戏剧性故事,但它的思路完全贴合普通人的直觉 ------ 比如你想找朋友圈里和你隔 3 个人的好友,就是先找直接好友(1 层)、再找他们的好友(2 层)、最后找这层人的好友(3 层),直到找到目标。

二、BFS 的核心作用:解决 "步数最少" 的问题

BFS 的核心价值就在于 "层层扩散" 的特性,主要能解决两类问题:

  1. 最核心 :在无权图(所有边没有权重 / 权重都相同) 中,找到从起点到目标的最短路径(步数最少) ------ 比如迷宫里 "最少走几步到出口"、朋友圈 "你和 XX 隔了几个人";
  2. 其他常用作用
    • 遍历图 / 树的所有节点(比如爬虫从一个网页出发,爬完整个网站的所有页面);
    • 判断两个节点是否可达(比如判断迷宫里起点能不能到出口、两个用户是否在同一个社交网络里);
    • 找离起点最近的所有目标(比如找你家周边 1 公里内的所有超市)。

三、BFS 的具体可执行代码(朋友圈找人示例)

下面用 "找朋友圈里和你隔几步的好友" 为例,写一个通俗易懂的 BFS 代码,注释详细,可直接复制运行。

python 复制代码
from collections import deque

def bfs_friend_circle(friend_graph, start_person, target_person):
    """
    BFS实现:找朋友圈中从start_person到target_person的最短步数(隔几个人)
    :param friend_graph: 朋友圈关系图,格式为 {人: [好友列表], ...}
    :param start_person: 起点(你)
    :param target_person: 目标(要找的人)
    :return: 最短步数(比如直接好友返回1,无交集返回-1),最短路径(比如["你", "张三", "李四"])
    """
    # 1. 异常处理:起点/目标不在朋友圈里
    if start_person not in friend_graph or target_person not in friend_graph:
        return -1, []
    # 2. 特殊情况:找自己
    if start_person == target_person:
        return 0, [start_person]
    
    # 3. 初始化:队列(存储待探索的人+当前步数+路径),已访问集合(避免重复找)
    # deque是Python的双端队列,popleft()效率高,适合BFS的"先进先出"
    queue = deque()
    queue.append((start_person, 0, [start_person]))  # (当前人, 步数, 路径)
    visited = set()
    visited.add(start_person)
    
    # 4. 核心循环:层层探索好友
    while queue:
        # 取出队列最前面的人(保证"层层处理")
        current_person, current_step, current_path = queue.popleft()
        
        # 遍历当前人的所有好友
        for friend in friend_graph[current_person]:
            # 如果好友是目标,直接返回结果
            if friend == target_person:
                new_path = current_path + [friend]
                return current_step + 1, new_path
            
            # 如果好友没被访问过,加入队列继续探索
            if friend not in visited:
                visited.add(friend)
                new_path = current_path + [friend]
                queue.append((friend, current_step + 1, new_path))
    
    # 5. 遍历完都没找到,说明无交集
    return -1, []

# ------------------- 测试代码 -------------------
if __name__ == "__main__":
    # 构建朋友圈关系图
    # 说明:"你"的好友是"张三""李四";"张三"的好友是"你""王五";"王五"的好友是"张三""赵六";以此类推
    friend_graph = {
        "你": ["张三", "李四"],
        "张三": ["你", "王五"],
        "李四": ["你", "赵六"],
        "王五": ["张三", "赵六"],
        "赵六": ["李四", "王五", "孙七"],
        "孙七": ["赵六"],
        "周八": ["吴九"],
        "吴九": ["周八"]
    }
    
    # 测试1:找"你"到"孙七"的最短步数和路径
    step, path = bfs_friend_circle(friend_graph, "你", "孙七")
    if step == -1:
        print("你和孙七不在同一个朋友圈里")
    else:
        print(f"你到孙七最短需要隔{step}个人,路径:{' -> '.join(path)}")
    
    # 测试2:找"你"到"周八"的最短步数和路径
    step2, path2 = bfs_friend_circle(friend_graph, "你", "周八")
    if step2 == -1:
        print("\n你和周八不在同一个朋友圈里")
    else:
        print(f"你到周八最短需要隔{step2}个人,路径:{' -> '.join(path2)}")
代码运行结果
复制代码
你到孙七最短需要隔3个人,路径:你 -> 张三 -> 王五 -> 赵六 -> 孙七

你和周八不在同一个朋友圈里
代码关键部分解释
  1. 队列(deque):BFS 的核心工具,用 "先进先出" 保证 "层层处理"------ 先处理完 "你" 的直接好友,再处理好友的好友,不会漏掉任何一层;
  2. 已访问集合(visited):避免重复探索(比如 "你" 找 "张三","张三" 又找 "你",会无限循环);
  3. 路径记录:每个队列元素都带 "当前路径",找到目标时直接返回完整路径,不用额外回溯;
  4. 步数计算:每往下一层,步数 + 1,保证返回的是 "最少步数"。

四、总结

  1. 故事核心:BFS 像 "迷宫里层层找出口",核心是 "先进先出、地毯式扩散",没有戏剧性发明故事,但贴合日常思维;
  2. 核心作用:解决无权图的 "最短步数" 问题,还能遍历图、判断节点是否可达(比如朋友圈是否有交集);
  3. 代码关键:用队列(deque)实现 "层层处理",用已访问集合避免循环,是入门图算法的首选。
相关推荐
u0109272715 分钟前
模板编译期排序算法
开发语言·c++·算法
GIS瞧葩菜14 分钟前
Cesium 轴拖拽 + 旋转圈拖拽 核心数学知识
人工智能·算法·机器学习
m0_6860416121 分钟前
C++中的适配器模式变体
开发语言·c++·算法
txzrxz21 分钟前
结构体排序,双指针,单调栈
数据结构·算法·双指针算法·单调栈·结构体排序
AndrewHZ25 分钟前
【AI黑话日日新】什么是AI智能体?
人工智能·算法·语言模型·大模型·llm·ai智能体
wWYy.26 分钟前
算法:二叉树最大路径和
数据结构·算法
葱明撅腚28 分钟前
利用Python挖掘城市数据
python·算法·gis·聚类
We་ct31 分钟前
LeetCode 36. 有效的数独:Set实现哈希表最优解
前端·算法·leetcode·typescript·散列表
weixin_3954489142 分钟前
main.c_cursor_0129
前端·网络·算法
CS创新实验室1 小时前
《计算机网络》深入学:路由算法与路径选择
网络·计算机网络·算法