引言

本文介绍了无向图的深度优先搜索和使用广度优先搜索寻找图中的路径,它们分别借助了栈(先进后出)和队列(先进先出)的特性来实现。

有关图的概念可参考博文数据结构之图的概述

深度优先搜索

类似树的深度优先遍历,所谓深度优先即递归的对相邻节点进行访问。从图来看即访问的越来越深,不撞南墙不回头!!


在访问某个顶点时:

  • 将它标记为已访问
  • 递归地访问它的所有没有标记过的邻接顶点
package com.algorithms.graph;/*** 图的深度优先搜索* @author yjw* @date 2019/5/16/016*/
public class DepthFirstSearch {/*** 标记是否被访问过*/private boolean[] marked;private int count;public DepthFirstSearch(Graph g,int s) {marked = new boolean[g.vertexNum()];dfs(g,s);}public boolean marked(int v) {return marked[v];}public int count() {return count;}private void dfs(Graph g,int v) {marked[v] = true;System.out.print(v + " ");count++;/*** 深度就是递归调用,* 访问某个顶点时,将它标记为已访问;* 递归地访问它所有没有被标记过的邻接点*/for (int w: g.adj(v)) {if (!marked[w]) {dfs(g,w);}}}
}

因为存在递归调用,因此底层是利用了栈来实现的。

使用广度优先搜索寻找图中的路径

给定一个起点s,若想寻找从s到某个顶点v的最短路径(所含边数最少),那么就要用到广度优先搜索。

从图来看是优先访问某顶点的相邻顶点,有点像生活中玻璃的裂缝效果。

上面说了深度优先搜索是基于栈的,而广度优先搜索是基于队列的。


先将起点加入队列,然后重复下列步骤直到队列为空:

  • 取队列中的下一个顶点v并标记它为已访问;
  • 将与v相邻的所有未被标记过的顶点加入队列
package com.algorithms.graph;import com.algorithms.queue.Queue;
import com.algorithms.stack.Stack;/*** @author yjw* @date 2019/5/20/020*/
public class BreadthFirstPaths {private boolean[] marked;/*** 到达当前顶点的最近顶点*/private int[] edgeTo;private final int s;public BreadthFirstPaths(Graph g, int s) {marked = new boolean[g.vertexNum()];edgeTo = new int[g.vertexNum()];this.s = s;bfs(g, s);}private void bfs(Graph g, int s) {Queue<Integer> queue = new Queue<>();marked[s] = true;queue.enqueue(s);while (!queue.isEmpty()) {int v = queue.dequeue();/*** 将与v相邻的所有未被标记的顶点加入队列*/for (int e: g.adj(v)) {if (!marked[e]) {marked[e] = true;edgeTo[e] = v;queue.enqueue(e);}}}}public boolean hasPathTo(int v) {return marked[v];}public Iterable<Integer> pathTo(int v) {if (!hasPathTo(v)) {return null;}Stack<Integer> path = new Stack<>();/*** 从路径终点一步步寻找前一个顶点*/for (int x = v; x != s ; x = edgeTo[x]) {path.push(x);}/*** 利用栈后进先出刚好可以顺序打印路径上所有顶点*/path.push(s);return path;}
}

其中QueueStack的实现见 栈和队列的实现

图论算法——无向图的深度优先搜索和广度优先搜索相关推荐

  1. 算法十——深度优先搜索和广度优先搜索

    文章出处:极客时间<数据结构和算法之美>-作者:王争.该系列文章是本人的学习笔记. 搜索算法 算法是作用于数据结构之上的.深度优先搜索.广度优先搜索是作用于图这种数据结构之上的.图上的搜索 ...

  2. 数据结构学习笔记——图的遍历算法(深度优先搜索和广度优先搜索)

    目录 一.图的遍历概念 二.深度优先搜索(DFS) (一)DFS算法步骤 1.邻接表DFS算法步骤 2.邻接矩阵DFS算法步骤 (二)深度优先生成树.森林 (三)DFS的空间复杂度和时间复杂度 三.广 ...

  3. 八数码深度优先搜索_深度优先搜索和广度优先搜索

    深度优先搜索和广度优先搜索 关于搜索&遍历 对于搜索来说,我们绝大多数情况下处理的都是叫 "所谓的暴力搜索" ,或者是说比较简单朴素的搜索,也就是说你在搜索的时候没有任何所 ...

  4. 深度优先遍历和广度优先遍历_图与深度优先搜索和广度优先搜索

    什么是图? 图是一种复杂的非线性表结构.由若干给定的点一级任意两点间的连线所构成.图通常用来描述事物之间的特定关系, 代表的就是事物, 线就是事物之间所具有的关系.例如社交网络就是一种典型的图关系, ...

  5. 深度优先搜索和广度优先搜索

    深度优先搜索和广度优先搜索 ​ 在人工智能的运筹学的领域中求解与图相关的应用中,这两个算法被证明是非常有用的,而且,如需高效地研究图的基本性质,例如图的连通性以及图是否存在环,这些算法也是必不可少的. ...

  6. 学会二叉树不知道干啥?二叉树的深度优先搜索和广度优先搜索,我要打十个乃至二十个(打开你的LeetCode撸起来)学练并举

    目录 一. 图解二叉树的深度优先搜索 二. 二叉树的广度优先搜索  (层序遍历) 三. 打开LeetCode 撸起来 至此, 咱多少被刚刚的后序非递归搞得可能有点小晕晕的, 没事,层序简单呀....  ...

  7. SDUT 2142 数据结构实验之图论二:基于邻接表的广度优先搜索遍历

    数据结构实验之图论二:基于邻接表的广度优先搜索遍历 Time Limit: 1000MS Memory Limit: 65536KB Submit Statistic Problem Descript ...

  8. 迷宫问题:深度优先搜索和广度优先搜索

    迷宫问题:深度优先搜索和广度优先搜索 1.深度优先搜索可以使用栈实现,栈顶元素为当前节点 2.当前节点搜索下一节点,判断节点是否走得通,如果走得通任意方向走一步,走不通一直弹出栈内元素,直到走得通 3 ...

  9. 深度优先搜索与广度优先搜索区别和案例

    今天周末,心血来潮打开LeetCode做一道题: https://leetcode-cn.com/problems/number-of-enclaves/ 看到题,我的第一想法是: 从边缘的陆地开始, ...

  10. 算法(6)深度优先搜索和广度优先搜索

    一.深度优先搜索(DFS) 主要思路: 从图中一个未访问的顶点 V 开始,沿着一条路一直走到底,然后从这条路尽头的节点回退到上一个节点,再从另一条路开始走到底,不断递归重复此过程,直到所有的顶点都遍历 ...

最新文章

  1. 阻塞队列与非阻塞队列
  2. 每天进步一点点——Linux文件锁编程flock
  3. 要强大的“黑匣子”,还是“可解释”的机器学习?| 清华AI Time激辩
  4. java try resource_从 Java 字节码角度看 try with resource 语法糖
  5. 使用Blazor做个简单的时间戳在线转换工具
  6. [Gamma阶段]展示博客
  7. CCNA笔记-各种路由器的接口
  8. 截取含HTML标签的字符串
  9. 网络货运平台要智能,安全的数据底座少不了
  10. Android 系统(57)---深入理解Android输入系统
  11. 手写一个动态代理实现,手写Proxy,手写ClassLoader,手写InvocationHandler
  12. 《软件测试技术实战:设计、工具及管理》—第2章 2.7节测试用例不应该包含实际的数据...
  13. CCF NOI1138 高精度加法
  14. DB2 V10.5 PureScale支持HADR
  15. python编程英语单词怎么写_用Python写一个背英文单词程序
  16. oracle中某字段显示long,ORACLE的ALL_VIEWS数据字典text字段long类型问题
  17. 火狐浏览器 附件组件 Xpath 使用
  18. XXXfragment that is not a fragment错误,fragment认不出来
  19. 7系列主板 规格对比
  20. Java大型CRM客户管理系统源码 带小程序 CRM小程序源码

热门文章

  1. SQL 和T-SQL学习(一)
  2. 未定义标识符_ConnectionPtr
  3. 主席树-----动态开点,不hash
  4. Tensorflow Python3 做神经网络(视频教程)
  5. 详解Oracle数据货场中三种优化:分区、维度和物化视图
  6. 把Vim改装成一个IDE编程环境
  7. Python学习Day06
  8. 【模板】线性筛法求素数
  9. Android Studio在创建项目是一直处于building “project name”gradle project info的解决办法...
  10. Http协议对格式、请求头、方法