问题是这样的:
用原生js求DOM树的最大深度?
好吧 这是我在
SegmentFault
上答的题目# 递归 ↵
我利用了
DOM
节点的 children
属性 来遍历和递归, children
代表子节点,是一个 类数组对象
因此常规的数组方法用不了,得自行封装。 (其实是不想写 for
)我的递归套路是:
叶子节点返回 1; 非叶子节点返回 (1 + 子节点们深度的最大值)
# 工具 ↵
刚刚提到了,
children
属性是类数组对象,因此常规的数组方法不能用,要自己封装。00// map(e => e + 1)([0, 1, 2]) 01// => 1, 2, 3 02// 类似于数组的map方法 不过这里柯里化了 03var map = cb => arr => Array.prototype.map.call(arr, cb); 04 05// 取数组最大值 06// max([0, 1, 2]) 07// => 2 08var max = arr => arr.reduce((acc, cur) => { 09 if (cur >= acc) return cur; 10 else return acc; 11}, arr[0]);
执行
map(e => e + 1)([0, 1, 2])
返回 [1, 2, 3]
执行
max([0, 1, 2])
返回 2
# 实现 ↵
00// 递归函数 01var nextChildren = node => { 02 // 基准条件 03 if (node.children.length === 0) return 1; 04 else { 05 // 求子节点们的长度 并取最大值 06 var deeps = map(nextChildren)(node.children); 07 08 return 1 + max(deeps); 09 } 10}
# 测试 ↵
先写一个测试函数,输入选择器,返回所有符合选择器节点们的深度。
00var getDeep = sel => { 01 let arr = document.querySelectorAll(sel); 02 03 return map(nextChildren)(arr); 04}
对我的博客做了测试:
首先是
getDeep('body')
结果是 [8]
再来是
.md
元素 结果是 [5, 4]
最后再看看
<html>
(结果应该是 body 的基础上 + 1)结果是
[9]
确实如此。再测了侧
<footer>
结果是 [3]
打开浏览器自己看了看确实是 3
结果
nextChildren 还是挺可靠的。