從遍歷Dom樹(shù),初識(shí)算法
參考文章:https://juejin.im/post/6844903731973062669
目的:自定義一個(gè)方法去檢查DOM中的某個(gè)元素
// HTML結(jié)構(gòu)如下
<div class="wrapper">
<section class="header">
<div class="logo"></div>
</section>
<section class="main">
<div class="sidebar">
<ul class="menu">
<li class='li'>
<a href="" id='demo'>li1-a</a>
</li>
<li class='li'>
<a href="">li2</a>
</li>
</ul>
</div>
</section>
<section class="footer">
<div class="copyright"></div>
</section>
</div>
思路和方案:
- 深度遍歷,利用遞歸實(shí)現(xiàn)
- 使用棧,深度優(yōu)先
- 廣度優(yōu)先,非遞歸實(shí)現(xiàn)
深度遍歷,利用遞歸實(shí)現(xiàn)
const cusGetElementByIdByDFS = function(parentNode, id) {
if(parentNode){
let target = null
const children = Array.from(parentNode.children)
if(parentNode.id === id) {
return parentNode
}
for(let i =0; i < children.length; i++){
target = cusGetElementByIdByDFS(children[i], id)
if(target) {
return target
}
}
}
return null
}
使用棧,深度優(yōu)先
const cusGetElementByIdByDFS2 = function(parentNode, id) {
if(!parentNode) {
return null
}
let stack = []
if(parentNode.id === id) {
return parentNode
}
parentNode.forEach(item =>{
stack.push(item)
})
while(stack.length > 0) {
let node = stack.pop()
if(node.id === id){
return node
} else {
if(node.children.length > 0) {
stack = Array.from(node.children).concat(stack)
}
}
}
}
廣度優(yōu)先,非遞歸實(shí)現(xiàn)
const cusGetElementByIdByDFS2 = function(parentNode, id) {
const layer = []
if ( parentNode ) {
layer.push({
node:parentNode,
dep:1
})
while( layer.length > 0 ){
let root = layer.shift() // 出隊(duì)列
if(root.id === id) {
return root
} else {
if(root.children.length > 0) {
Array.from(root.children).forEach(node=>{
layer.push({
node,
dep: item.dep++
})
})
}
}
}
}
return null
}