如何在纯JavaScript中获取给定元素的所有父节点?

问题描述 投票:0回答:7
为元素的例子the the是:

<A>

	

小一点(而且更安全,因为找不到
[HTML, BODY, DIV, DIV, P, SPAN, A]
):
javascript dom
7个回答
67
投票
target


您可以尝试以下操作:

var a = document.getElementById("target");
var els = [];
while (a) {
    els.unshift(a);
    a = a.parentNode;
}

26
投票
我喜欢这种方法:

var nodes = []; var element = document.getElementById('yourelement'); nodes.push(element); while(element.parentNode) { nodes.unshift(element.parentNode); element = element.parentNode; }
... $ 0是您的元素。
此方法的好处是它可以用作表达式的值。

10
投票

[...(function*(e){do { yield e; } while (e = e.parentNode);})($0)]


您可以沿着

[...(function*(e){while (e = e.parentNode) { yield e; }})($0)]

S的链条行走,直到达到虚假价值,并在您走时附加到一个数组:



5
投票

const getParents = el => { for (var parents = []; el; el = el.parentNode) { parents.push(el); } return parents; }; const el = document.querySelector("b"); console.log(getParents(el).reverse().map(e => e.nodeName));


注意逆转是在呼叫者中完成的,因为它对于谱系算法不是必不可少的。映射到
<div><p><span><b>Foo</b></span></div>
纯粹用于呈现和非必需品。
注意,这种方法意味着您将以文档元素作为链中的最后一个元素结束。如果您不想要那个,则可以将
e.nodeName
添加到循环停止条件中。
上面代码的总体时间复杂性是线性的,
&& el !== document

是在就地的,因此不需要额外的分配。正如其他一些答案所建议的那样,在循环中是二次的,可能会损害罕见的深层树木的可扩展性,以换取优雅的可忽略的增益。

其他替代方案(基于

这):

reverse()


我认为,如果您经常使用此功能,那么在大多数情况下,这很可能是长期运行

。 t会更具性能的原因是因为它最初检查以查看可能遇到的祖先的深度。另外,该功能并非每次调用时都会创建一个新数组,而是有效地重复使用相同的数组,并切成薄片,在某些浏览器中非常优化。但是,由于我知道没有真正有效的方法来检查最大深度,因此我对查询效率低下的检查。

unshift
上述函数的浏览器兼容性是它将在边缘工作,但在IE中不起作用。如果您需要IE支持,那么您将需要一个
for(var e = document.getElementById("target"),p = [];e && e !== document;e = e.parentNode) p.push(e);

polyfill。

2
投票

0
投票
对象,因此,如果您只需要元素,则可能需要在代码中进一步排除这些对象。

您可以在MDN文章中阅读的阴影根周围的一些微妙之处,但是您的代码很可能不会具有阴影根,因此它要简单得多,并且只会将一个数组从事件的目标返回到根节点。 请参见Https://developer.mozilla.org/en-us/docs/web/api/event/composedpath

document

window


0
投票
在JavaScript Array中获取儿童的所有父节点

<html>
  <body>
    <div>
      <button onclick="onClick">Click me</button>
    </div>
  </body>
</html>

知道更多

	
© www.soinside.com 2019 - 2025. All rights reserved.