JavaScript中的child和childNodes有什么区别?


305

我发现自己使用JavaScript,并且遇到了childNodeschildren属性。我想知道它们之间有什么区别。还有一个相对于另一个而言更可取吗?

Answers:


330

了解这.childrenElement的属性。1只有Elements具有.children,并且这些子元素都是Element类型的。2

但是,这.childNodesNode的属性。.childNodes可以包含任何节点。3

一个具体的例子是:

let el = document.createElement("div");
el.textContent = "foo";

el.childNodes.length === 1; // Contains a Text node child.
el.children.length === 0;   // No Element children.

大多数情况下,您想使用它,.children因为通常您不想在DOM操作中遍历TextComment节点。

如果确实要操作“文本”节点,则可能需要.textContent替代。4


1.从技术上讲,它是ParentNode的属性,Element所包含的mixin。
2.它们都是元素,因为.childrenHTMLCollection,只能包含元素。
3.同样,.childNodes可以容纳任何节点,因为它是NodeList
4.或者.innerText。在此处此处查看差异。


3
是的,IE似乎有一些问题:quirksmode.org/dom/w3c_core.html#t71
Felix Kling

4
实际上,子元素是父节点接口的属性,而不是元素。usonsci.wordpress.com/2014/09/30/html-children-vs-childnodes
胜利者

似乎iOS 8.3(也许还有其他人?)不支持.childrenXML文档jsfiddle.net/fbwbjvch/1
Saebekassebil,2015年

4
仅在具有XML节点的Microsoft Edge上遇到此问题。看来Microsoft Edge不喜欢孩子。很好,我不想复制该浏览器。
Dan-Nolan

1
“元素与节点”的自然跟进:stackoverflow.com/questions/132564/…–
user1454265

23

Element.children仅返回元素子代,而Node.childNodes返回所有节点子代。请注意,元素是节点,因此两者在元素上均可用。

我相信childNodes是更可靠的。例如,MDC(在上面链接)指出IE仅children在IE 9中正确 childNodes


2
天哪,如果仅在IE 6-8上有效,那将是梦想成真。
Ry-

3
@minitech它确实有效(对于某些有价值的工作)。显然.children不会过滤掉注释节点,但是会过滤掉文本节点。
雷诺斯2011年

2
@Raynos:完全相同.getElementsByTagName('*')。有时IE可能会令人讨厌...
Ry-

children支持IE的shim / polyfill实现。
wrlee '18

7

到目前为止,很好的答案是,我只想补充一点,您可以使用来检查节点的类型nodeType

yourElement.nodeType

这将为您提供一个整数:(从此处获取

| Value |             Constant             |                          Description                          |  |
|-------|----------------------------------|---------------------------------------------------------------|--|
|    1  | Node.ELEMENT_NODE                | An Element node such as <p> or <div>.                         |  |
|    2  | Node.ATTRIBUTE_NODE              | An Attribute of an Element. The element attributes            |  |
|       |                                  | are no longer implementing the Node interface in              |  |
|       |                                  | DOM4 specification.                                           |  |
|    3  | Node.TEXT_NODE                   | The actual Text of Element or Attr.                           |  |
|    4  | Node.CDATA_SECTION_NODE          | A CDATASection.                                               |  |
|    5  | Node.ENTITY_REFERENCE_NODE       | An XML Entity Reference node. Removed in DOM4 specification.  |  |
|    6  | Node.ENTITY_NODE                 | An XML <!ENTITY ...> node. Removed in DOM4 specification.     |  |
|    7  | Node.PROCESSING_INSTRUCTION_NODE | A ProcessingInstruction of an XML document                    |  |
|       |                                  | such as <?xml-stylesheet ... ?> declaration.                  |  |
|    8  | Node.COMMENT_NODE                | A Comment node.                                               |  |
|    9  | Node.DOCUMENT_NODE               | A Document node.                                              |  |
|   10  | Node.DOCUMENT_TYPE_NODE          | A DocumentType node e.g. <!DOCTYPE html> for HTML5 documents. |  |
|   11  | Node.DOCUMENT_FRAGMENT_NODE      | A DocumentFragment node.                                      |  |
|   12  | Node.NOTATION_NODE               | An XML <!NOTATION ...> node. Removed in DOM4 specification.   |  |

请注意,根据Mozilla

以下常量已被弃用,不再应使用:Node.ATTRIBUTE_NODE,Node.ENTITY_REFERENCE_NODE,Node.ENTITY_NODE,Node.NOTATION_NODE


0

选择一种取决于您要寻找的方法!?

我将使用ParentNode.children

由于它提供的namedItem方法可以让我直接获取子元素之一,而无需遍历所有子元素或避免使用getElementById等。

例如

ParentNode.children.namedItem('ChildElement-ID'); // JS
ref.current.children.namedItem('ChildElement-ID'); // React
this.$refs.ref.children.namedItem('ChildElement-ID'); // Vue

我将使用Node.childNodes

因为它提供了forEach我使用window.IntersectionObserver 例如时的方法

nodeList.forEach((node) => { observer.observe(node) })
// IE11 does not support forEach on nodeList, but easy to be polyfilled.

在Chrome 83上

Node.childNodes提供entriesforEachitemkeyslengthvalues

ParentNode.children提供itemlengthnamedItem

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.