<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>深度遍历和广度遍历测试</title>
<style type="text/css"> </style>
</head>
<body>
<div class="box">
<ul class="menus">
<li class="item1"><i class="item1-icon"></i><span class="item1-content">菜单1</span></li>
<li class="item2"><i class="item2-icon"></i><span class="item2-content">菜单2</span></li>
<li class="item3"><i class="item3-icon"></i><span class="item3-content">菜单3</span></li>
</ul>
</div>
<script>
console.log('深度优先递归');
DFTRecur(document.body,[],function(item){
console.log(item);
}); console.log('深度优先非递归');
let res = DFT(Array.from(document.body.children),function(item){
// if(item.className == 'item2-content'){
// console.log('taget item', item);
// return true;
// }
console.log(item);
}); console.log('广度优先递归');
BFTRec(document.body,[]); console.log('广度优先非递归');
BFT(Array.from(document.body.children)); //深度优先搜索的递归写法
function DFSRecur(root,stack,fVistor) {
let b = false;
if (root != null) {
stack.push(root);
//函数fVistor,节点传入函数,节点一旦满足某种条件,就返回true
//可以在找到第一个满足条件的节点后,就停止遍历
if(fVistor(root))return true; var children = root.children;
if(children){
for (var i = 0; i < children.length; i++){
b = DFTRecur(children[i],stack,fVistor);
//有一个子节点满足条件就停止循环
if(b) break;
}
}
//当前节点及其子节点都不满足条件就出栈
if(!b) stack.pop();
}
return b;
} //深度优先遍历的递归写法,深度优先遍历递归,不需要使用栈,通常是使用先序遍历,即先遍历根节点,再遍历所有子节点
function DFSRecur(root,stack,fVistor) {
if (root != null) {
fVistor(root) var children = root.children;
if(children){
for (var i = 0; i < children.length; i++){
DFTRecur(children[i],stack,fVistor);
}
}
}
} //深度优先遍历的非递归写法
function DFT(root,fVistor) {
fVistor = fVistor || console.log;
if (root != null) {
//兼容root为数组,且从前往后深度遍历
var stack = [].concat(root).reverse(); while (stack.length != 0) {
var item = stack.pop();
//满足条件就break,使得方法兼具深度优先搜索的功能,找到就跳出循环,停止查找
if(fVistor(item)) break;if(item.children) stack.push(...Array.from(item.children).reverse());
}
}
} //广度优先遍历的递归写法,广度优先的递归和非递归写法都需要队列
function BFTRec(root,queue,fVistor){
fVistor = fVistor || console.log;
if(root != null){
queue.push(root);
//满足条件return,使该方法兼具广度优先搜索的功能,找到就停止遍历
if(fVistor(root)) return;
//先访问下一个兄弟节点,递归会一直横向访问,直至横向访问完毕
BFTRec(root.nextElementSibling,queue,fVistor);
//回到本行的第一个节点root
root = queue.shift();
//跳到root节点的下一行的第一个节点,又会开始横向遍历
BFTRec(root.firstElementChild,queue,fVistor);
}
} //广度优先遍历的非递归写法
function BFT(root,fVistor) {
fVistor = fVistor || console.log;
if (root != null) {
//兼容root为数组情况
var queue = [].concat(root);
while (queue.length != 0) {
var item = queue.shift();
//找到就break,使得方法兼具广度优先搜索功能,找到就停止遍历
if(fVistor(item)) break;
if(item.children) queue.push(...item.children);
}
}
}
</script>
</body>
</html>

Dom的深度优先遍历和广度优先遍历的更多相关文章

  1. 深度优先遍历 and 广度优先遍历

    深度优先遍历 and 广度优先遍历 遍历在前端的应用场景不多,多数是处理DOM节点数或者 深拷贝.下面笔者以深拷贝为例,简单说明一些这两种遍历.

  2. js实现深度优先遍历和广度优先遍历

    深度优先遍历和广度优先遍历 什么是深度优先和广度优先 其实简单来说 深度优先就是自上而下的遍历搜索 广度优先则是逐层遍历, 如下图所示 1.深度优先 2.广度优先 两者的区别 对于算法来说 无非就是时 ...

  3. C++ 二叉树深度优先遍历和广度优先遍历

    二叉树的创建代码==>C++ 创建和遍历二叉树 深度优先遍历:是沿着树的深度遍历树的节点,尽可能深的搜索树的分支. //深度优先遍历二叉树void depthFirstSearch(Tree r ...

  4. 邻接矩阵c源码(构造邻接矩阵,深度优先遍历,广度优先遍历,最小生成树prim,kruskal算法)

    matrix.c #include <stdio.h> #include <stdlib.h> #include <stdbool.h> #include < ...

  5. C++编程练习(9)----“图的存储结构以及图的遍历“(邻接矩阵、深度优先遍历、广度优先遍历)

    图的存储结构 1)邻接矩阵 用两个数组来表示图,一个一维数组存储图中顶点信息,一个二维数组(邻接矩阵)存储图中边或弧的信息. 2)邻接表 3)十字链表 4)邻接多重表 5)边集数组 本文只用代码实现用 ...

  6. js实现对树深度优先遍历与广度优先遍历

    深度优先与广度优先的定义 首先我们先要知道什么是深度优先什么是广度优先. 深度优先遍历是指从某个顶点出发,首先访问这个顶点,然后找出刚访问这个结点的第一个未被访问的邻结点,然后再以此邻结点为顶点,继续 ...

  7. python、java实现二叉树,细说二叉树添加节点、深度优先(先序、中序、后续)遍历 、广度优先 遍历算法

    数据结构可以说是编程的内功心法,掌握好数据结构真的非常重要.目前基本上流行的数据结构都是c和c++版本的,我最近在学习python,尝试着用python实现了二叉树的基本操作.写下一篇博文,总结一下, ...

  8. 【图的遍历】广度优先遍历(DFS)、深度优先遍历(BFS)及其应用

    无向图满足约束条件的路径 •[目的]:掌握深度优先遍历算法在求解图路径搜索问题的应用 [内容]:编写一个程序,设计相关算法,从无向图G中找出满足如下条件的所有路径:  (1)给定起点u和终点v.  ( ...

  9. 二叉树的深度优先遍历与广度优先遍历 [ C++ 实现 ]

    深度优先搜索算法(Depth First Search),是搜索算法的一种.是沿着树的深度遍历树的节点,尽可能深的搜索树的分支. 当节点v的所有边都己被探寻过,搜索将回溯到发现节点v的那条边的起始节点 ...

随机推荐

  1. Thinkphp 取消Url默认模块的现实

    例子http://www.tp.com/home/index/index 想要现实的效果是:http://www.tp.com/index/index 1是通过配置路由来达到目的 2通过配置首页的入口 ...

  2. struts2之标签库

    使用Struts2标签的准备工作: 导入Struts2标签库,该标签定义文件位于 struts2-core-2.3.16.3.jar 的 METE-INF下的struts-tag.tld文件. < ...

  3. attention发展历史及其相应论文

    这个论文讲述了attention机制的发展历史以及在发展过程的变体-注意力机制(Attention Mechanism)在自然语言处理中的应用 上面那个论文提到attention在CNN中应用,有一个 ...

  4. photoshop入门笔记1:PS的快捷键

    PS部分快捷键: 1.魔棒的作用:比较快捷的抠图工具,对于一些分界线比较明显的图像,通过魔棒工具可以很快速的将图像抠出,魔棒的作用是可以知道你点击的那个地方的颜色,并自动获取附近区域相同的颜色,使它们 ...

  5. 硬盘安装Windows Server 2008(解决系统盘符变成D盘)

    硬盘安装Windows 2008系统方法 操作系统最好用的无疑是server 2003,但是现在Server 2003支持的软件越来越少,很多是故意不支持Server 2003了, 像php5.5以上 ...

  6. Linux设置下载站点

    https://blog.csdn.net/jfhkd2012/article/details/50912757

  7. linux c scanf()小解

    今天学习了新的内容,关于c语言的scanf()函数. scanf()函数,读取指定格式的值赋值给相应变量.空格(‘ ‘),回车('\n'),TAB是分隔符,轻易不会被读取.还有,该函数的返回值是正确读 ...

  8. python基础之闭包函数和装饰器

    补充:全局变量声明及局部变量引用 python引用变量的顺序: 当前作用域局部变量->外层作用域变量->当前模块中的全局变量->python内置变量 global关键字用来在函数或其 ...

  9. Hibernate---数据操作示例BY实体类注释

    通过实体的映射文件创建表的示例,除了基本jar包外,还需要jar包如下 ejb3-persistence.jar.hibernate-annotations.jar这两个包均在hibernate-an ...

  10. laravel5.5契约

    无规矩不成方圆, Laravel 的契约是一组定义框架提供的核心服务的接口,规定了实现该接口的规范. 为什么要使用接口 首先,让我们来看一些高耦合缓存实现的代码.如下: <?php namesp ...