6

我试图在 JavaScript(不使用 jQuery)中获取页面上具有特定类名的所有元素的列表。因此,我使用 getElementsByClassName() 函数如下:

var expand_buttons = document.getElementsByClassName('expand');
console.log(expand_buttons, expand_buttons.length, expand_buttons[0]);

请注意,我的页面上有三个锚元素,其类为“expand”。这个 console.log() 输出

[] 0 undefined

接下来,为了好玩,我将 expand_buttons 放入它自己的数组中,如下所示:

var newArray = new Array(expand_buttons);
console.log(newArray, newArray.length);

这突然输出

[NodeList[3]] 1

我可以点击节点列表并查看页面上三个“展开”锚元素的属性。还值得注意的是,我能够让我的代码在w3schools 测试页面中运行。

还可能值得注意的是,我对 document.getElementsByName 的使用实际上确实输出(到控制台)一个元素数组,但是当我询问它的长度时,它告诉我 0。同样,如果我尝试使用访问数组元素array_name[0]像往常一样,它输出“未定义”,尽管当我将对象打印到控制台时,数组中显然有一个元素。

有人知道为什么会这样吗?我只想循环遍历 DOM 元素,目前我正在避免使用 jQuery,因为我正在尝试使用 vanilla JavaScript 进行编码。

谢谢,

典范RG

4

2 回答 2

10

它不是一个 JavaScript 的东西,而是一个 Web 浏览器的东西。该 API 由本机对象(document对象)提供,并且根据 DOM 规范,它返回一个 NodeList 对象。您可以将 NodeList 视为一个数组,它很相似,但明显不同(正如您所注意到的)。

您始终可以将 NodeList 复制到新数组:

var nodeArr = Array.prototype.slice.call(theNodeList, 0);

或者在现代 ES2015 环境中:

var nodeArr = Array.from(theNodeList);

JavaScript 总是存在于某些运行时上下文中,并且该上下文可以包括为 JavaScript 代码提供便利的各种 API。Web 浏览器就是其中之一。DOM 以一种并非特别偏向于 JavaScript 的方式指定;这是一个语言中立的接口定义。

我想这个答案的简短版本是,“因为它就是这样。”

于 2012-06-16T15:08:40.203 回答
3

它不返回数组,因为它返回的对象是 "live",特别是它是一个 live NodeList

在大多数情况下,NodeList 是一个实时集合。这意味着 DOM 树上的更改将反映在集合上。

于 2012-06-16T15:11:27.740 回答