I'm trying to understand the best way to optimize performance in JavaScript. To simplify, I have some code where a bunch of buttons are each associated with a specific element, and I need to be able to make changes to both the button and its associated element whenever a button is clicked.
I have been told it is better to consolidate event handlers with event delegation where you can. I've also been told if I can avoid querying the DOM over and over for the same element, better to do it just once and store that for later. But in this case, it seems like I need to do one or the other, so I'm wondering which is more costly? Currently I have the following code that runs once to set things up:
buttons.forEach((button) => {
const area = document.querySelector(`#${button.getAttribute('aria-controls')}`);
button.addEventListener('click', (e) => {
// do some things with "area" and "button"
});
});
Obviously this creates an individual listener for each button, so I was thinking I could rewrite it like this:
document.addEventListener('click', (e) => {
if(e.target.classList.contains("button-class")) {
const area = document.querySelector(`#${e.target.getAttribute('aria-controls')}`);
// do some things with "area" and "button"
}
});
But is this worth the trade off that now every time a button is clicked I have to query for the associated "area" element again? Does the answer change depending on how many buttons I have or how often they are likely to be clicked? Is there some third answer that is more optimal than either of my solutions? Apologies if this is a really obvious and stupid question, but I've been googling and looking through other Stack Overflow questions and really can't find anything to answer this.
which is more costly?
As you already noticed, it's a trade-off. The costs you need to compare are respectively
For just a few buttons, that are clicked in normal web flows (and not, say, an APM testing tool), it really doesn't matter.