NodeList

Baseline 已广泛支持

此特性已相当成熟,可在许多设备和浏览器版本上使用。自 ⁨2015 年 7 月⁩以来,各浏览器均已提供此特性。

NodeList 对象是 节点 的集合,通常由 Node.childNodes 等属性和 document.querySelectorAll() 等方法返回。

这个接口曾是 创建不可修改列表的尝试,并且至今仍然被支持,以免破坏现有代码。现代 API 使用基于 JavaScript 数组 的类型来表示列表结构,从而提供了许多数组方法,同时对其使用施加了额外的语义(例如,使其项只读)。

这些历史原因并不意味着开发者应该避免使用 NodeList。你不会自己创建 NodeList 对象,而是从 Document.querySelectorAll() 等 API 获取它们,这些 API 并未被弃用。但是,要注意它与真实数组的语义差异。

虽然 NodeList 不是 Array,但可以使用 forEach() 迭代它。也可以使用 Array.from() 将其转换为真实的 Array

实时 NodeLists 与静态 NodeLists

尽管它们都被视为 NodeList 对象,但 NodeList 有 2 种变体:实时 (live)静态 (static)

在大多数情况下,NodeList实时的,这意味着 DOM 的更改会自动更新集合。

例如,Node.childNodes 是实时

js
const parent = document.getElementById("parent");
let childNodes = parent.childNodes;
console.log(childNodes.length); // let's assume "2"
parent.appendChild(document.createElement("div"));
console.log(childNodes.length); // outputs "3"

在其他情况下,NodeList静态的,DOM 的任何更改都不会影响集合的内容。无处不在的 document.querySelectorAll() 方法是唯一返回静态 NodeList 的 API。

在选择如何迭代 NodeList 中的项以及是否应该缓存列表的 length 时,牢记这种区别很有好处。

实例属性

NodeList.length 只读

NodeList 中的节点数。

实例方法

NodeList.item()

按索引返回列表中的一项,如果索引超出范围则返回 null

访问 nodeList[i] 的替代方法(当 i 超出范围时,它会返回 undefined)。这对于非 JavaScript DOM 实现非常有用。

NodeList.entries()

返回一个 迭代器,允许代码遍历集合中的所有键/值对。(在这种情况下,键是从 0 开始的整数,值为节点。)

NodeList.forEach()

NodeList 中的每个元素执行一次提供的函数,并将元素作为参数传递给函数。

NodeList.keys()

返回一个 迭代器,允许代码遍历集合中的所有键/值对的键。(在这种情况下,键是从 0 开始的整数。)

NodeList.values()

返回一个 迭代器,允许代码遍历集合中的所有键/值对的值(节点)。

示例

可以使用 for 循环来遍历 NodeList 中的项。

js
for (let i = 0; i < myNodeList.length; i++) {
  let item = myNodeList[i];
}

请勿使用 for...in 来枚举 NodeList 中的项,因为它们还会枚举其 lengthitem 属性,如果你的脚本假设只需要处理 element 对象,则会导致错误。此外,for...in 不保证按特定顺序访问属性。

for...of 循环可以正确地遍历 NodeList 对象。

js
const list = document.querySelectorAll("input[type=checkbox]");
for (const checkbox of list) {
  checkbox.checked = true;
}

浏览器还支持迭代器方法(forEach())以及 entries()values()keys()

规范

规范
DOM
# interface-nodelist

浏览器兼容性