文章目录

  • BFS算法框架
    • 框架代码
  • 简单题:二叉树的最小高度
  • 拔高题:解开密码锁的最少次数
    • 一波优化:双向BFS

BFS算法框架

BFS算法和DFS算法属于图论算法的范畴,DFS在前面回溯中,可以去看一下。
BFS算法用于寻找两点之间的最短路径。

碧如说:寻找树的最小高度(迭代法)、走迷宫、导航等问题。
这些问题看起来都会比较抽象,去做也是很抽象。

与其说算法框架难写,倒不如说是把实际问题转化为算法问题来的要难。
还记得我在图论算法那篇里面有讲过:学习图论算法,最难的是要有用图论算法的意识。等下看了例题就知道了。


框架代码

这个代码其实就是微调一下图的BFS遍历,搞成个伪代码的样子,没什么新鲜的。

int BFS(Node start,Node target){/*这是一个BFS算法的代码框架return:返回从start到target的最短步数start:起始点target:终点*/Queue<Node> q;Set<Node> 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())  //cur.adj()泛指与cur相邻的节点if(x not in visited){q.offer(x);visited.add(x);}} step++;   //更新步数}
}

简单题:二叉树的最小高度

不难吧,用递归的话一下就出来了。
不过现在不是在讲BFS嘛,那就用BFS的方法吧。

起点是什么?起点是根节点。终点是什么?终点就是最靠近根节点的、两个子节点都是Null的节点。

接下来,我们对上面的框架进行改造:

int minDepth(TreeNode root){/*这是一个求二叉树最小高度的函数return:二叉树的最小高度root:根节点*/if(root == NULL) return 0;Queue<TreeNode> q;q.offer(root);   //将起点加入队列int depth = 1;    while(!q.isEmpty()){int sz = q.size();for(int i = 0; i<sz; i++){TreeNode cur = q.poll();//判断是否到终点if(cur.left == NULL && cur.right == NULL)return depth;//将cur相邻节点加入队列if(cur.left != NULL)q.offer(cur.left);if(cur.right != NULL)q.offer(cur.right);}  depth++;  //更新步数}return depth;
}

拔高题:解开密码锁的最少次数

你有一个带有四个圆盘拨轮的轮盘锁,每个拨轮都有“0-9”十个数字,旋转没有边界限制,但是每次只能旋转一个位置。轮盘锁的初始位置是“0000”,现在给你一个密码和一组死亡密码(避免拨出的密码),请你设计一个算法,计算从初始状态到拨出最终密码所需要的最少次数。

抽象吧,就直接看这个题目,直接给我干懵逼了。
但是,不怕啊,前面不是说过了动态规划类题目的解题步骤嘛,先把暴力解法画出来,走通一条路,再优化。

那,暴力解法怎么解?真的,要不是有那个“死亡密码组”的存在,还真的就很暴力了。

第一步,拨一下。不管会怎么样,都得拨一下吧。这一下有八种可能了吧。
第二步,匹配。拨一下,对所有结果都进行一次的匹配。如果对上了,就返回结果;如果对不上,返回第一步再循环。
注意点一:如果碰到死亡密码,跳过。
注意点二:不要走回头路。
注意点三:空间能省着用就省着用。

好,关键的一步来了,怎么将这个暴力算法往图论算法的方向去引呢。
再看一下上面这个暴力算法,不难看出来,这就是一个节点下面拖八个子节点的八叉树,又是求最短距离,BFS。

int openLock(String[] deadends,String target){//纪录需要跳过的死亡密码Set<String> deads = new HashSet<>();for(String s:deadends) dead.add(s);//纪录已经穷举过的密码set<String> visited = new HashSet<>();Queue<String> q = new LinkedList<>();//从起点开始启动广度优先搜索int step = 0;q.offer("0000");visited.add("0000");while(!q.isEmpty){int sz = q.size();for(int i = 0;i<sz;i++){string cur = q.poll();//判断密码是否合法if(deads.contains(cur)continue;if(cur.equals(target))return step;}//将一个节点的未遍历相邻节点加入队列for(int j=0;j<4;j++){String up = plusOne(cur,j);if(!visited.contains(up){q.offer(up);visited.add(up);}String down = minusOne(cur,j);if(!visited.contains(down){q.offer(down);visited.add(down);}}step++;}return -1;
}

上翻下翻的代码:

String plusOne(String s,int j){char[] ch = s.toCharArray();if(ch[j] == '9')ch[j] = '0';elsech[j] += 1;return new String(ch);
}
String downOne(String s,int j){char[] ch = s.toCharArray();if(ch[j] == '0')ch[j] = '9';elsech[j] -= 1;return new String(ch);
}

一波优化:双向BFS

上面的操作,简化一下是这样的:

从顶部蓝色的节点,找底部红色的节点。

所有节点都被遍历了。

这时候我们换个思路,既然终点也是已知的,那就:

上下同步进行,在中间黑色节点的地方汇聚了。

【C++】算法集锦(5):BFS算法相关推荐

  1. 自动寻路算法C语言,bfs算法(c语言贪吃蛇自动寻路算法)

    广度优先法(BFS)算法C/C++代码,要说明和图解!谢谢! #include #define MAX 10 int front=-1,rear=-1; struct node { int value ...

  2. 【算法】广度遍历算法的应用 求出距离顶点v0的最短路径长度为最长的一个顶点,图结构的bfs生成树及其双亲表示形式

    例: 求出距离顶点v0的最短路径长度为最长的一个顶点,并要求尽可能节省时间 分析: 用bfs算法(利用bfs算法的层次特性): 从v0出发进行广度遍历时, 最后一层的顶点距离v0的最短路径长度最长.因 ...

  3. 图像保边滤波算法集锦系列

    在美颜算法的实现中,如何既能把人脸皮肤磨得光滑,雀斑磨得干净,又能保留五官的自然清晰,这就需要一种能保留边缘信息的平滑滤波器,这种滤波器的好坏在一定程度上,也就影响了美颜磨皮效果的好坏,对此,本人将在 ...

  4. A*算法(一)算法导言

    A*算法(一)算法导言 1. 问题场景 2. 结点图 3. 其他搜索算法 3.1 Dijkstra算法 3.2 BFS算法 3.3 存在障碍的情况 3.4 取长补短 4. A*算法 1. 问题场景 已 ...

  5. 遍历所有点的最短路径python_图遍历算法之最短路径Dijkstra算法

    一.最短路径问题(shortest path problem) 最短路径问题是图论研究中一个经典算法问题,旨在寻找图中两节点或单个节点到其他节点之间的最短路径.根据问题的不同,算法的具体形式包括: 确 ...

  6. 广度优先搜索 BFS算法

    广度优先搜索算法(Breadth-First-Search,BFS),又称作宽度优先搜索.BFS算法是从根节点开始,沿着树的宽度遍历树的节点.如果所有节点均被访问,则算法中止. 算法思想 1.首先将根 ...

  7. matlab 算法集锦

    算法集锦 决策树-划分点 function [n,h]=huafendian1(x) %n返回增益 %h返回划分点 %假设0代表第一类 %假设1代表第二类 %输入x第一列为属性,第二列为用于学习的分类 ...

  8. 数据结构常见算法集锦

    数据结构经典算法集锦 第2章 线性表 KMP算法 //获得next数组 void GetNext(char *t, int next[MAX]) {int i = 1, j = 0;next[1] = ...

  9. 数据结构经典算法集锦

    数据结构经典算法集锦 第2章 线性表 KMP算法 //获得next数组 void GetNext(char *t, int next[MAX]) {int i = 1, j = 0;next[1] = ...

  10. STL经典算法集锦之排列(next_permutation/prev_permutation

    STL经典算法集锦之排列(next_permutation/prev_permutation) 来自:CSDN博客推荐文章 | 时间:2012-05-07 14:54:09 原文链接: http:// ...

最新文章

  1. 很多人都在埋怨没有遇到好的团队,但好的团队不可能凭空出现,一流的团队不能仅靠团队成员努力,作为Leader,要有可行的规划,并坚定地执行、时势地调整(转)...
  2. Web APi之控制器选择Action方法过程(九)
  3. 【错误记录】Kotlin 1.5.0 编译报错 ( 1.5.0 中 Float 不能直接转 Byte 类型 )
  4. mysql 查看编码方式_Mysql查看编码方式专题
  5. Kibana_X-Pack管理Elasticsearch权限
  6. java+selenium报异常org.openqa.selenium.StaleElementReferenceException的解决方案
  7. caffe 使用小技巧
  8. 求助各位大神JSP报错急急急!!!!感激不尽
  9. Codecademy-中文JavaScript系列教程-初认JS
  10. Canvas-lms 开源在线学习管理系统源码部署(生产版)
  11. android 日志打印内容完全相同,Log的chatty机制,identical 391 lines
  12. MyBatis高频面试题
  13. CSTC 2001 聪明的学生 BZOJ 2523 递归(类搜索,推理)
  14. LeetCode994 Rotting Oranges解题方案
  15. vc60.pdb打不开怎么办
  16. 写文三年了,给大家说点儿心里话
  17. 金色耶路撒冷 感受圣城之圣
  18. sql语句中的or用法(及与and和in区别)
  19. LeetCode 526. 优美的排列
  20. 物联网通信协议(接入协议)

热门文章

  1. 按键云数据仓库平台 ,连接按键精灵和云端数据库,可自行配置用做网络验证或云端配置
  2. 地区三级联动数据库(中国行政区划分数据库)【2018年1月】
  3. pano2vr.exe下载
  4. 小葫芦弹幕助手连接服务器失败,为什么自动弹幕发送老是失败?如何解决?
  5. 移动前端开发和 Web 前端开发的区别是什么
  6. Revit API: Material 材质
  7. dtu连接mysql_数据中心使用dtu远程连接oracel 9i数据库问题
  8. 测试进阶必备,这5款http接口自动化测试工具不要太香~
  9. 23 - OAI NSA gNB搭建 - 博一
  10. 回文数c语言(来源:力扣(LeetCode))