算法之BFS算法框架

作者的话:最近有点时间,开始回来写写算法相关的文章

BFS算法框架

前言

BFS(广度优先级搜索)和DFS(深度优先级搜索)是比较常用的算法,其中DFS算是一种回溯算法,在二叉树中就相当于前序遍历算法。这里先分析BFS算法,为什么呢?因为BFS比较简单!废话少说,直接上分析!

算法分析

BFS相对于DFS最主要的区别在于:BFS找到的路径一定是最短的,但是空间复杂度比DFS要大很多

BFS算法的核心思想实际上就是将问题抽象成“图”,从一个点开始,向周围扩散。一般来说,我们写BFS算法常用的数据结构是“队列”,每次都将一个节点周围的所有节点加入队列。

BFS算法是出现的场景实际上就是让你在一幅“图”里面找出从“起点”到“终点”的最短距离。把算法本质搞清楚之后,问题都能化归为基本问题。

如果上面的分析有点枯燥?不要紧,直接上栗子:

如走迷宫,有的格子周围的墙壁不能走,让你算从起点到终点的最短距离是多少?如果这个迷宫某些格子有“传送门”呢?

再比如有两个单词,要求通过替换某些字母,把其中一个变成另外一个,每次只能替换一个字母,最少要替换几次?

再比如连连看游戏,消除两个方块的条件不仅仅是图案相同,还要保证两个方块之间的最短连线不能多于两个两个拐点。你玩连连看,点击两个坐标,程序是如何找到最短连线的?如何判断最短连线有几个拐点?

。。。

其实,上面的例子无一不是一幅“图”,让你从起点走到终点,问最短路径,实则BFS本质。

BFS算法框架

上面分析完了,下面直接上算法框架伪代码:

// 计算从起点 start 到终点 target 的最近距离
int BFS(Node start, Node target) {
    Queue q; // 核心数据结构
    Set visited; // 避免走回头路

    q.offer(start); // 将起点加入队列
    visited.add(start);
    int step = 0; // 记录扩散的步数

    while (q not empty) {
        int sz = q.size();
        /* 将当前队列中的所有节点向四周扩散 */
        for (int i = 0; i < sz; i++) {
            Node cur = q.poll();
            /* 划重点:这里判断是否到达终点 */
            if (cur is target)
                return step;
            /* 将 cur 的相邻节点加入队列 */
            for (Node x : cur.adj())
                if (x not in visited) {
                    q.offer(x);
                    visited.add(x);
                }
        }
        /* 划重点:更新步数在这里 */
        step++;
    }
}

记住:因为BFS都是每次都是所有节点一起遍历,因此BFS总能比较快地找到最短路径。

你可能感兴趣的:(算法,bfs)