classList.remove是从HTMLCollection中删除元素的?

Sea*_*ean 7 javascript

我在使用JavaScripts新的classList API时遇到了一些非常奇怪的行为,比如说我们有以下HTML代码:

<p class="testing">Lorem Ipsum</p>
<p class="testing">Lorem Ipsum</p>
Run Code Online (Sandbox Code Playgroud)

以下JavaScript代码:

var elements = document.getElementsByClassName("testing");
alert(elements.length);
elements[0].classList.remove("testing");
alert(elements.length);
Run Code Online (Sandbox Code Playgroud)

第一个警报将为您提供值2,而第二个警报返回1.

似乎从元素中删除类也将其从elementsHTMLCollection中删除,这对我来说完全没有意义.

您可以在此处查看此代码的示例.

尝试使用如下代码从某些元素中删除某个类时遇到此问题:

var elements = document.getElementsByClassName('testing');
var elementsLength = elements.length - 1;
for(var i = 0; i <= elementsLength ; i++)
{
    elements[i].classList.remove('testing');
}
Run Code Online (Sandbox Code Playgroud)

假设我们有两个元素,如上例所示,循环第一次成功运行,但第二次它在HTMLCollection中寻找不再存在的元素,所以我得到类似"TypeError:elements [i] undefined" ".

您可以在此处查看上述代码的示例

至少可以说这是令人沮丧的,我无法理解为什么/如何在调用classList.remove函数之前,classList.remove只会影响一次有效的数组集.我甚至无法在网上找到有关此行为的任何信息.

我在疯狂吗?或者我是否挖掘了一些没有人知道的classList api的奇怪隐藏功能?

pla*_*alx 9

返回的集合document.getElementsByClassName是实时的,因此如果元素不再具有该类,则它将从集合中删除.

您可以创建集合的非实时副本:

var elements = [].slice.call(document.getElementsByClassName('testing'));
Run Code Online (Sandbox Code Playgroud)

或者考虑到它的存在:

while (elements.length) elements[0].classList.remove('element-focus');
Run Code Online (Sandbox Code Playgroud)

  • @SeanDunwoody我不确定什么是保持集合与DOM同步的底层实现,但是从MDN"HTML DOM中的HTMLCollections是实时的;它们在基础文档被更改时自动更新**". . (2认同)