5

If I do this:

document.getElementById("myDiv").innerHTML = "some_html_code";

will that create nodes in my DOM three as it would if I used appendChild()?

Reason for asking is that I'm creating a mobile application where memory usage must be low. I don't want to create a lot of nodes.

  • 4
    Yes, it creates the nodes. And they're removed when you empty the div. – Denys Séguret Dec 04 '12 at 16:21
  • 1
    One thing to keep in mind is that using `innerHTML` is that you will lose any event handlers you may have created inside `#myDiv`. – Chris Sobolewski Dec 04 '12 at 16:23
  • @ChrisSobolewski Good point! And also that you cannot bind new event handlers (other than inline handlers in the string) – Ian Dec 04 '12 at 16:24
  • Something to look at for maybe helping decide which to use? http://stackoverflow.com/questions/2305654/innerhtml-vs-appendchildtxtnode – Ian Dec 04 '12 at 16:26
  • @Ian, it is added to dom, but i cant add new handlers? –  Dec 04 '12 at 16:26
  • @IntoTheVoid Sorry, what I mean is that you cannot bind events directly to the innerHTML text elements. After you set the innerHTML (as long as this is a live DOM element), you can bind event handlers, but not before – Ian Dec 04 '12 at 16:27

3 Answers3

7

It is roughly the same as

var div = document.getElementById("myDiv");

while( div.firstChild ) {
    div.removeChild( div.firstChild );
}

div.appendChild( document.createTextNode("a_html_string") );

Of course, if by "html_string" you mean a string consisting of complex html, then of course nodes are created from the html as appropriate (element nodes, comment nodes, text nodes etc). But a simple string of text is simply a single text node.

So if your html string were '<div id="hello">world</div>', that would roughly be:

var div = document.getElementById("myDiv");

while( div.firstChild ) {
    div.removeChild( div.firstChild );
}

var anotherDiv = document.createElement("div");
anotherDiv.setAttribute("id", "hello");
anotherDiv.appendChild(document.createTextNode("world"));
div.appendChild(anotherDiv);

It is probably shocking how much is happening with a simple innocent looking .innerHTML setter, and this is not even including parsing the html.

It's important to note that none of this is garbage, all of those objects created are necessary. To make sure you are only creating necessary nodes, do not use unnecessary whitespace between nodes. For example

<span>hello</span> <span>world</span>

is 3 text nodes but

<span>hello</span><span> world</span>

is only 2 text nodes.

A long while ago I created a facetious jsfiddle that converts html to "DOM code" for all of those .innerHTML haters.

Esailija
  • 138,174
  • 23
  • 272
  • 326
4

Yes, the innerHTML will be parsed and the nodes will be created. There's no way around it, the DOM is made of nodes.

bfavaretto
  • 71,580
  • 16
  • 111
  • 150
  • exactly! this should be the answer to the question. – GottZ Dec 04 '12 at 16:26
  • 1
    Agreed, but I don't think the OP is trying to avoid "creating nodes" (your second sentence) – Ian Dec 04 '12 at 16:29
  • @Ian, I think the OP is. Otherwise, what does "garbage" mean in the question, and why the statement about memory consumption? – bfavaretto Dec 04 '12 at 16:33
  • I think they mean the "memory consumption" necessary for creating nodes explicitly (instead of the magic by `innerHTML`). As I re-read the question, I see what you mean, nevermind :) – Ian Dec 04 '12 at 17:12
1

It will create string "a_html_string" and it will be displayed. but you can also append elements:

document.getElementById("myDiv").innerHTML = "<a> Link </a>"; // will be displayed "Link"
karaxuna
  • 26,752
  • 13
  • 82
  • 117