我有一个段落元素的集合。有些是空的,有些只包含空格,而有些则有内容:
<p>Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Vestibulum tortor quam, feugiat vitae, ultricies eget, tempor sit amet, ante. Donec eu libero sit amet quam egestas semper. Aenean ultricies mi vitae est. Mauris placerat eleifend leo.</p>
<p></p>
<p> </p>
<p> </p>
<p> </p>
<p> </p>
我正在使用 getElementsByTagName
来选择它们:
var paragraphs = document.getElementsByTagName('p');
这将返回文档中的所有段落。我想删除所有这些,所以我想运行
for (var i = 0, len = paragraphs.length; i < len; i++) {
paragraphs[i].remove();
}
但我得到 Uncaught TypeError: Cannot read property 'remove' of undefined
错误。我觉得这很奇怪,但我会尝试添加一个守卫,看看会发生什么:
for (var i = 0, len = paragraphs.length; i < len; i++) {
paragraphs[i] && paragraphs[i].remove();
}
没有错误,但并未删除所有元素。所以我再次运行它,它删除 了一些 以前没有删除的元素。我 再次 运行它, 最后 所有段落都从文档中删除。
我想知道我在这里遗漏了什么明显的细节。
原文由 Marc Kline 发布,翻译遵循 CC BY-SA 4.0 许可协议
问题是
paragraphs
是一个 实时列表。通过删除p
元素,您还更改了该列表。一个简单的解决方法是以 相反的顺序 遍历列表:替代解决方案是创建一个 静态列表(非实时列表)。您可以通过以下任一方式执行此操作:
Array
:document.querySelectorAll
:然后,您可以按常规顺序遍历列表(使用
for
循环):或者(使用
for...of
循环):请注意
.remove
是一种相对较新的 DOM 方法,并非每个浏览器都支持。有关详细信息,请参阅 MDN 文档。为了说明这个问题,假设我们有一个包含三个元素的节点列表
paragraphs = [p0, p1, p2]
。那么当您遍历列表时会发生这种情况:所以在这个例子中,
p1
没有被删除,因为它被跳过了。