These days that I have been working with javascript for DOM manipulation, I realized that I can bring a group of elements by its class name in two ways:
-
document.getElementsByClassName()
; -
document.querySelectorAll()
;
However, none of them is better than another because they should be used according to the structure that we have in our HTML and our needs. But! it's important that we have to take into consideration the output of each of them and understand how they work.
Theory
According to MDN documentation:
-
getElementsByClassName() returns a live
HTMLCollection
representing an array-like object of all child elements which have all of the given class name(s). -
querySelectorAll() returns a static (not live)
NodeList
representing a list of the document's elements that match the specified group of selectors.
That being said, I questioned myself what the heck means a live HTMLCollection
and a static NodeList
? From there, let me explain to you in a better way this difference.
Hands-on
Let's consider the following HTML structure:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Demo</title>
</head>
<body>
<ul id="list">
<li class="item">First Item</li>
<li class="item">Second Item</li>
<li class="item">Third Item</li>
</ul>
<script src="script.js"></script>
</body>
</html>
Now, let's get the items by their class name item
in the two ways mentioned above:
We can see that both brought all the elements that I needed with the class item
. However, there is a big difference in the data structure they were returned.
Now, let's add a new <li>
element to our list, and let's add some javascript code to our script.js file.
//get UL element
const list = document.getElementById('list');
//Get items by class name (two ways)
const itemsByClassName = document.getElementsByClassName('item');
const itemsByQuerySelector = document.querySelectorAll('.item');
console.log('First console log', itemsByClassName, itemsByQuerySelector);
//adding the fourth element
list.innerHTML += `<li class="item">Fourth Item</li>`;
console.log('Second console log', itemsByClassName, itemsByQuerySelector);
Let's see the results!
We can see that the new item was added to the list, though, the HTMLCollection
was updated with the fourth item and the NodeList
still has the first three elements, it didn't realize that there was a change in our list.
Therefore, this is the big reason why HTMLCollection
is a live data structure and NodeList
is a static data structure. At first hand the HTMLCollection
updates itself automatically every time it detects a change in the items that were retrieved by the method. On the other hand, NodeList
will remain the same since the moment we executed it no matter the changes that occur in our HTML.
Conclusion
To sum up, feel free to use them, but take into consideration this huge difference to decide which of them suits you better according to your needs.
For more information, check these resources out:
Thanks for reading!
Top comments (7)
I have a confusion here. is it a necessity that every Nodelist must be static? (sorry for my English)
"NodeLists behave differently depending on how you access them; if you access elements using childNodes, the returned list is live and will update as more elements are added to the node. If it’s accessed using querySelectorAll(), the returned list is static and will not update if more elements are added to the node."
medium.com/@layne_celeste/htmlcoll...
This helps me a lot ! M a newbie at Full-Stack and was looking for resources to help me understand the differences and common stuff between HTML collection and node list .Thank u so much kind sir !
Thanks a lot, it's a useful article and it's characterized by simplicity.
Guessing this has something to do with a reference vs value assignment when creating the array like objects.
thank you soo much , I like This article , I understand it now😁
Thank you sir, That’s crystal clear👏🏿