为什么要y.innerHTML = x.innerHTML;避免? [英] Why should y.innerHTML = x.innerHTML; be avoided?

查看:168
本文介绍了为什么要y.innerHTML = x.innerHTML;避免?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

让我们说,我们有一个DIV X 在页面上,我们想复制(复制 - 粘贴),该DIV的内容到另一个DIV 。我们可以做到这一点,像这样:

Let's say that we have a DIV x on the page and we want to duplicate ("copy-paste") the contents of that DIV into another DIV y. We could do this like so:

y.innerHTML = x.innerHTML;

或使用jQuery:

$(y).html( $(x).html() );

然而,看来这方法是不是一个好主意,并且应该避免。

However, it appears that this method is not a good idea, and that it should be avoided.

(1)为什么应避免使用这种方法吗?

(1) Why should this method be avoided?

(2)应如何来代替呢?

(2) How should this be done instead?

更新:结果
对于这个问题的缘故,让我们假设有ID为的没有任何元素的DIV X 里面。结果
(对不起,我忘了覆盖这种情况下,我原来的问题。)

Update:
For the sake of this question let's assume that there are no elements with ID's inside the DIV x.
(Sorry I forgot to cover this case in my original question.)

结论:结果
我已经发布了我自己的答案下面这个问题(因为我本来打算)。现在,我还刨去接受我自己的答案:P ,但lonesomeday的回答是如此惊人,我不得不接受它吧。

Conclusion:
I have posted my own answer to this question below (as I originally intended). Now, I also planed to accept my own answer :P, but lonesomeday's answer is so amazing that I have to accept it instead.

推荐答案

从一个地方到另一个地方复制HTML元素的这种方法是一个什么样的浏览器做了misap prehension的结果。浏览器不保留在内存中的HTML文档的地方,并反复修改HTML基础上通过JavaScript命令。

This method of "copying" HTML elements from one place to another is the result of a misapprehension of what a browser does. Browsers don't keep an HTML document in memory somewhere and repeatedly modify the HTML based on commands from JavaScript.

当浏览器首次加载页面时,它的分析的HTML文档,并把它变成一个DOM结构。这是一个对象遵循W3C标准的关系(当然,主要是...)。原始的HTML是从那时候开始完全是多余的。浏览器不关心什么原始的HTML结构为;其网页的理解是,从它创建的DOM结构。如果你的HTML标记是不正确的/无效,它将在由网络浏览器的一些方法进行校正; DOM结构将不包含在任何方式无效code

When a browser first loads a page, it parses the HTML document and turns it into a DOM structure. This is a relationship of objects following a W3C standard (well, mostly...). The original HTML is from then on completely redundant. The browser doesn't care what the original HTML structure was; its understanding of the web page is the DOM structure that was created from it. If your HTML markup was incorrect/invalid, it will be corrected in some way by the web browser; the DOM structure will not contain the invalid code in any way.

基本上,HTML应视为连载一个DOM结构通过互联网被传递或存储在一个文件在本地的一种方式。

Basically, HTML should be treated as a way of serialising a DOM structure to be passed over the internet or stored in a file locally.

它不应该,因此,可用于修改现有的网页。 DOM(文档对象模型)具有用于改变网页的内容的系统。这是基于节点的关系,而不是上的HTML序列化。因此,当你添加一个 UL ,你有这两个选项(假设 UL 是列表元素):

It should not, therefore, be used for modifying an existing web page. The DOM (Document Object Model) has a system for changing the content of a page. This is based on the relationship of nodes, not on the HTML serialisation. So when you add an li to a ul, you have these two options (assuming ul is the list element):

// option 1: innerHTML
ul.innerHTML += '<li>foobar</li>';

// option 2: DOM manipulation
var li = document.createElement('li');
li.appendChild(document.createTextNode('foobar'));
ul.appendChild(li);

现在,第一个选项看起来很简单,但是这仅仅是因为浏览器已经提取了大量离开你:在内部,浏览器必须元素的儿童转换为字符串,然后附加一些内容,然后转换字符串返回到一个DOM结构。第二个选项对应于发生了什么事情的浏览器的原生理解。

Now, the first option looks a lot simpler, but this is only because the browser has abstracted a lot away for you: internally, the browser has to convert the element's children to a string, then append some content, then convert the string back to a DOM structure. The second option corresponds to the browser's native understanding of what's going on.

第二个主要的考虑因素是考虑HTML的限制。当你想到一个网页,不相关的元素都可以被序列化到HTML。例如,事件处理程序绑定 x.onclick =功能(); x.addEventListener(...)不会在的innerHTML 复制的,所以他们不会被复制跨越。因此,在 Y中的新元素将不会有事件侦听器。这可能不是你想要的。

The second major consideration is to think about the limitations of HTML. When you think about a webpage, not everything relevant to the element can be serialised to HTML. For instance, event handlers bound with x.onclick = function(); or x.addEventListener(...) won't be replicated in innerHTML, so they won't be copied across. So the new elements in y won't have the event listeners. This probably isn't what you want.

所以,解决这个问题的方法是与本地DOM方法工作:

So the way around this is to work with the native DOM methods:

for (var i = 0; i < x.childNodes.length; i++) {
    y.appendChild(x.childNodes[i].cloneNode(true));
}

阅读MDN文档可能会有助于理解做事是这样的:

Reading the MDN documentation will probably help to understand this way of doing things:

现在这个问题(与方案2中的code上面的例子)是它的非常的冗长,远长于的innerHTML 选择是。这是当你有一个JavaScript库,做这样的事情对你的AP preciate。例如,在jQuery的:

Now the problem with this (as with option 2 in the code example above) is that it is very verbose, far longer than the innerHTML option would be. This is when you appreciate having a JavaScript library that does this kind of thing for you. For example, in jQuery:

$('#y').html($('#x').clone(true, true).contents());

这是很多更加明确要发生什么。除了具有多种性能优势,preserving事件处理程序,例如,它也可以帮助你了解你的code在做什么。这有利于你的灵魂作为一个JavaScript程序员,使离奇失误显著不太可能!

This is a lot more explicit about what you want to happen. As well as having various performance benefits and preserving event handlers, for example, it also helps you to understand what your code is doing. This is good for your soul as a JavaScript programmer and makes bizarre errors significantly less likely!

这篇关于为什么要y.innerHTML = x.innerHTML;避免?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆