Różnica między DOM parentNode i parentElement

500

Czy ktoś może mi wyjaśnić tak prosto, jak to możliwe, jaka jest różnica między klasycznym DOM ParentNode a nowo wprowadzonym w Firefox 9 parentElement

shabunc
źródło
4
ParentNode wydaje się być standardem DOM, więc bezpieczniej jest zawsze używać go zamiast parentElement.
TMS
5
@TMS w3school nie jest autorytetem: w3fools.com
Guillaume Massé

Odpowiedzi:

486

parentElement jest nowy w Firefoksie 9 i DOM4, ale był obecny we wszystkich innych głównych przeglądarkach od wieków.

W większości przypadków jest to to samo co parentNode. Jedyna różnica pojawia się, gdy węzeł parentNodenie jest elementem. Jeśli tak, parentElementto jest null.

Jako przykład:

document.body.parentNode; // the <html> element
document.body.parentElement; // the <html> element

document.documentElement.parentNode; // the document node
document.documentElement.parentElement; // null

(document.documentElement.parentNode === document);  // true
(document.documentElement.parentElement === document);  // false

Ponieważ <html>element ( document.documentElement) nie ma elementu nadrzędnego, który jest elementem, parentElementjest null. (Są inne, bardziej mało prawdopodobne, przypadki, w których parentElementmogą być null, ale prawdopodobnie nigdy ich nie spotkasz).

samotny dzień
źródło
162
Innymi słowy, jest to całkowicie bezcelowe 99,99999999999999% czasu. Czyj to był pomysł?
Niet the Dark Absol
25
Oryginał parentElementbył zastrzeżoną rzeczą IE; Wierzę, że inne przeglądarki w tym czasie (np. Netscape) były obsługiwane, parentNodeale nie parentElement. (Oczywiście, biorąc pod uwagę, że wspomniałem o Netscape, mówię o drodze powrotnej do IE5 i wcześniejszych ...)
nnnnnn
9
@lonesomeday zapomniałeśdocumentfragment.firstChild.parentElement === null
Raynos
7
@Raynos To była właśnie dokładna okoliczność, którą miałem na myśli w ostatnim zdaniu mojej odpowiedzi ...
lonesomeday
17
Jak właśnie odkryłem, w elemencie SVG (takim jak circlewnętrze a g) w IE parentElementbędzie niezdefiniowany i parentNodebędzie tym, czego szukasz. :(
Jason Walton
94

W Internet Explorerze parentElementjest niezdefiniowany dla elementów SVG, natomiast parentNodejest zdefiniowany.

szybowiec
źródło
10
szczerze mówiąc, myślę, że jest to raczej komentarz niż odpowiedź.
shabunc
38
Prawdopodobnie, ale to jest powód, dla którego uderzyłem głową o stół przez godzinę lub dłużej, dopóki się nie domyśliłem. Podejrzewam, że wielu innych przychodzi na tę stronę po podobnym uderzeniu głową.
Speedplane
3
@speedplane Cieszę się, że to odpowiedź, ponieważ nie ma to żadnego logicznego sensu i kazałem mi się zastygać przez dłuższą chwilę ...
superphonic
1
Niezdefiniowane również dla węzłów komentarzy. W Chrome z radością otrzymywałem nadrzędny komentarz, ale w IE nie został zdefiniowany.
Simon_Weaver
Nie mogłem znaleźć źródła tego. parentElementniewdrożenie Nodejest dobrze znane ( developer.mozilla.org/en-US/docs/Web/API/Node/… ), ale dla SVGElement? Nie mogłem również odtworzyć tego document.createElement('svg').parentElementw IE 11.737.17763.0. Czy w międzyczasie można to naprawić?
epsilon
14

Użyj .parentElementi nie możesz się pomylić, dopóki nie korzystasz z fragmentów dokumentu.

Jeśli korzystasz z fragmentów dokumentów, potrzebujesz .parentNode:

let div = document.createDocumentFragment().appendChild(document.createElement('div'));
div.parentElement // null
div.parentNode // document fragment

Również:

let div = document.getElementById('t').content.firstChild
div.parentElement // null
div.parentNode // document fragment
<template id="t"><div></div></template>


Widocznie <html>„s .parentNodelinki do Dokumentu . Należy to uznać za decyzję, ponieważ dokumenty nie są węzłami, ponieważ węzły są zdefiniowane jako zawierające dokumenty i dokumenty nie mogą być zawarte w dokumentach.

Pacerier
źródło
6

Podobnie jak w przypadku nextSibling i nextElementSibling , pamiętaj tylko, że właściwości z „elementem” w nazwie zawsze zwracają Elementlub null. Właściwości bez mogą zwracać dowolny inny rodzaj węzła.

console.log(document.body.parentNode, "is body's parent node");    // returns <html>
console.log(document.body.parentElement, "is body's parent element"); // returns <html>

var html = document.body.parentElement;
console.log(html.parentNode, "is html's parent node"); // returns document
console.log(html.parentElement, "is html's parent element"); // returns null
Buksy
źródło
1
tak, ale w przeciwieństwie do następnych węzłów tekstowych lub węzłów komentarzy nie można nadrzędny.
Jasen
0

jest jeszcze jedna różnica, ale tylko w Internet Explorerze. Występuje podczas mieszania HTML i SVG. jeśli rodzic jest „drugim” z tych dwóch, to .parentNode daje rodzicowi, a .parentElement daje niezdefiniowany.

mathheadinclouds
źródło
1
Myślę, że undefinednie null.
Brian Di Palma