innerHTML versus the DOM: Can’t we all just get along?

April 19, 2008, 11:11 pm · Filed under: JavaScript

Having tested the relative speed of innerHTML versus DOM node replacement myself, I read with interest When innerHTML isn’t Fast Enough. I have put together a test of my previous 2 techniques plus one inspired by that article.

andrew.hedges.name



I am a web developer, living and working in New Zealand. I’m into my family, photography and frisbee sports.

The time will come when men such as I will look upon the murder of animals as they now look on the murder of men.
Leonardo da Vinci


Meta Me

LinkedIn
Twitter
Facebook
Ma.gnolia
Zooomr


Topics

Apple · Business · Coda · Design · Google · JavaScript · jQuery · Life · Marketing · New Mexico · New Zealand · PHP · Politics · Ruby on Rails · Twitter · Usability · Web Development · Widgets


Archives


Most Popular

Defeat comment spam? Yes we can! · The first 48 hours of PHP Function Reference, by the numbers · There is too much. Let me sum up. · What will be your legacy? · Make long URLs short with tr.im.it · On the value of Twitter · Coda 1.5 is the bee’s knees · Series on hold: What a surprise… · Radiant JavaScript Singletons Freelance Down Under · innerHTML versus the DOM: Can’t we all just get along?


Most Recent

Defeat comment spam? Yes we can! · There is too much. Let me sum up. · What will be your legacy? · Make long URLs short with tr.im.it · On the value of Twitter · Ego-surfing, 2001 style! · Stack Overflow: I’m sold! · V8: neither all that nor a bag of chips · Playing to a browser’s strengths: Simple Templates 1.1 · Introducing jQuery Simple Templates


Recent Reads

Encouraged Commentary · Google Weather API informal documentation · html5.org - HTML revisited · Introduction to WAI ARIA · bookoutlines / Predictably Irrational · The Rise of HTML5 · Five CSS design browser differences I can live with · HTML 5: The Markup Language · Avoiding Silos: “link” as a first-class object · The facade design pattern in JavaScript

See more @ Ma.gnolia


Friends

80/20 · 90 Seven Design · Alyson Hurt · Brian Warren · Daniel Lyons · Daniel Schwartz · David Hedges · Joshua Sallach · Kelly Green · Mark Bixby · Method Arts · Morgan Pyne · Piers Harding · Rob Pongsajapan · Ryan Park · seven-gen · Vaughan Rowsell · Vincent Thomé · Voom Studio


Recommended Books on
Web Development

My bias is for references over “cookbooks.” I want to know all of my options, not just one way to do something. Show me the why as well as the how and I am happy.

JavaScript: The Good Parts · JavaScript: The Definitive Guide · Designing with Web Standards · CSS: The Definitive Guide · Prioritizing Web Usability · The Elements of User Experience · Don't Make Me Think: A Common Sense Approach to Web Usability


Subscribe

Atom · RSS 2.0


I’ve hosted this website with pair Networks since 1997. They rock.

This blog is powered by software I wrote. Want some of that? Hire me.

Each of the buttons below writes the phrase Chubby bunny 10,000 times to the container div, clears the content, then does it again. What I’m trying to test here is the effect of the different ways of clearing out the DOM nodes from the container. Code and discussion follows.

innerHTML

This technique is the simplest and, probably, the most common on the web today. The following code builds up a long string of HTML, dumps it into the innerHTML attribute of the container div, then sets the content back to an empty string. Rinse, and repeat.

// Start 1st pass
innerHTML  = [];
iterations = iters + 1;
while (--iterations > 0) {
  innerHTML[innerHTML.length] = htmlDiv;
}
resultDiv.innerHTML = innerHTML.join('');
resultDiv.innerHTML = '';

// Start 2nd pass
innerHTML  = [];
iterations = iters + 1;
while (--iterations > 0) {
  innerHTML[innerHTML.length] = htmlDiv;
}
resultDiv.innerHTML = innerHTML.join('');

DOM replace

The following code builds up a document fragment by appending div nodes to it. The fragment is then appended to the container, a new fragment is built up, then the nodes are swapped out in one step.

// Start 1st pass
container  = document.createDocumentFragment();
iterations = iters;
container.appendChild(nodeDiv);
while (--iterations > 0) {
  container.appendChild(container.firstChild.cloneNode(true));
}
resultDiv.appendChild(container);

// Start 2nd pass
cloneDiv    = resultDiv.cloneNode(false);
cloneDiv.id = 'result-domreplace';
container   = document.createDocumentFragment();
iterations  = iters;
container.appendChild(nodeDiv);
while (--iterations > 0) {
  container.appendChild(container.firstChild.cloneNode(true));
}
resultDiv.parentNode.replaceChild(cloneDiv, resultDiv);
cloneDiv.appendChild(container);

innerHTML + DOM replace

The following code combines inserting a string of HTML via the innerHTML attribute with the one-step swapping goodness of the DOM replace code.

// Start 1st pass
innerHTML  = [];
iterations = iters + 1;
while (--iterations > 0) {
  innerHTML[innerHTML.length] = htmlDiv;
}
resultDiv.innerHTML = innerHTML.join('');

// Start 2nd pass
container  = resultDiv.cloneNode(false);
innerHTML  = [];
iterations = iters + 1;
while (--iterations > 0) {
  innerHTML[innerHTML.length] = htmlDiv;
}
container.innerHTML = innerHTML.join('');
resultDiv.parentNode.replaceChild(container, resultDiv);

View full source code

In theory, the last technique should be the fastest because the bottleneck with innerHTML is in removing the nodes by setting its value to an empty string. By building up a document fragment then swapping it out with the parentNode.replaceChild technique, we avoid using innerHTML to tear down the DOM.

In my testing, however, results were all over the shop. In Firefox, the results were as I expected: innerHTML was slowest, DOM replacement faster, and the combo technique fastest. In Internet Explorer, innerHTML was the fastest, the combo technique nearly as fast, and straight DOM manipulation nearly an order of magnitude slower. In Safari 3, I found no significant difference among the 3 techniques.

The following numbers are averages of 5 runs of each technique in the various browsers, expressed in milliseconds.


innerHTML DOM replacement innerHTML + DOM
Safari 3 109 104 96
Safari 2 489 849 457
Firefox 3b4 1588 1030 523
Firefox 2 1386 1019 401
IE 8b1 900 2131 844
IE 7 290 1275 475
IE 6 339 1880 373
Opera 9.27 266 847 675

From the above, it looks like the biggest advantage of the combo technique is its consistency across browsers. While straight innerHTML is faster on some browsers and straight DOM manipulation is faster on others, combining the 2 techniques yields decent performance across browsers.

Update: I added numbers for Safari 2, IE 8b1 and Opera 9.27 to the list above. My conclusion still appears to hold.

Fin

Comments close automatically after 15 days.
Still have something to say? Drop me a line!