JavaScript中两种DOM元素检测方式的时间复杂度是否等价?
DOM contains()两种写法的性能对比解答
你假设contains()是遍历所有子元素及后代逐一检查匹配,这个理解其实有偏差——浏览器原生的contains()方法并不是通过遍历所有后代节点来判断,而是利用DOM节点本身的层级关联(比如内部的节点树索引、parentNode链)来做快速判断,底层实现非常高效,几乎没有遍历开销。
基于这个前提,我们来对比两种写法的开销:
第一种:直接检查父元素及其后代
parentElement.contains(someChild);
这是最直接高效的写法,一次调用原生方法就能完成判断,底层不需要遍历所有后代,性能开销极小。
第二种:仅检查父元素的直接子元素
Array.from(parentElement.children).some(child => child.contains(e.target));
这种写法的开销明显更大,原因有几点:
- 首先要把
parentElement.children(一个HTMLCollection类数组对象)转成数组,这一步会产生额外的内存占用和操作开销; - 其次
some()方法会遍历父元素的直接子元素,每遍历一个就调用一次contains()——虽然单个contains()高效,但如果直接子元素数量多,就会多次调用原生方法; - 最坏情况下(目标元素不在任何直接子元素的后代里),需要遍历所有直接子元素并调用
contains(),开销远大于第一种写法。
你的判断是正确的,第二种写法的开销确实比第一种大很多,而且第一种写法逻辑更简洁,是更优的选择。
内容的提问来源于stack exchange,提问作者Oscar
相关产品推荐
相关产品推荐

