gpt4 book ai didi

javascript - 动态添加/删除 HTML 时防止内存泄漏

转载 作者:塔克拉玛干 更新时间:2023-11-02 20:49:32 26 4
gpt4 key购买 nike

我正在使用 PhoneGap 和 JQuery Mobile 创建一个应用程序,我希望从某些后端服务读取数据并根据收到的内容添加/删除列表项(也可能是 div)。当然,我想防止应用程序因长时间使用而速度减慢太多。

在添加/删除 HTML 方面是否有任何通用的最佳实践?我对此很陌生,所以我不太了解 DOM 的工作原理等等。

目前我正在使用 JQuery 的 append 将 HTML 行添加到某个容器 div,并使用 .html("") 删除一个元素。这是可以接受的,还是有更好的方法?

编辑:供您引用,我使用的是 JQuery Mobile 1.1.0 和 Phonegap 1.9.0。不知道这是否有帮助,但你去吧。

我希望在尽可能多的移动设备上使用这个应用程序,但我猜 iOS 和 Android 是目前最大的市场。

需要澄清的是,我实际上还没有遇到重大问题(目前),我只是想避免以后遇到任何问题而不得不通过大量代码来尝试解决问题。我认为如果我们能就一组最佳实践达成一致,即使用 innerHTML() 而不是 .append、remove 与 innerHTML("") 等等,我认为这对每个人都有用 :P

一些示例代码:

function changeList(sel){
var xmlfolder="/"
var name = sel[sel.selectedIndex].value+".xml";
var location= xmlfolder+name;
var list = document.getElementById("opList"); //opList is the container
list.innerHTML=""; //what i'm using to remove the previous occupant
//: is there a better way of doing this?
//reading stuff
$.ajax({

type:'GET',
cache: false,
url: location,
dataType:"xml",
success: function(data){
xmlInfo=data;


var i=0;
$(data).find("data").each(function(){

var string = "";
var sName=$(this).find("name").text();

string +=("<li>");
string +=("<a href=#details data-transition = slide >");
string+= sName;
string+="</a></li>";
$('#opList').append(string); //is there a better way of appending?
i++;

})

$('#opList').listview('refresh');

},
error:function(e){
alert("failed D:");
console.log(e);
}

});

}

最佳答案

我只是想向您抛出一些想法,我们看看有什么用!

确保编造您的 HTML 并将其一次性全部添加到 DOM,而不是在循环中添加点点滴滴。

例如(这样做):

var arr    = ['Title 1', 'Title 2', 'Title 3'],
output = [];

for (var i = 0, len = arr.length; i < len; i++) {
output.push('<li>' + arr[i] + '</li>');
}
$('ul').append(output.join(''));

请注意我只选择一次容器,这是关键,即使您确实必须在循环内引用 DOM 元素,请确保缓存对循环外元素的引用,否则您会不必要地做额外的事情每次迭代都工作。

例如(不要这样做,DOM 元素缓存除外,这很好):

var arr = ['Title 1', 'Title 2', 'Title 3'],
$ul = $('ul');

for (var i = 0, len = arr.length; i < len; i++) {
$ul.append('<li>' + arr[i] + '</li>');
}

如果您要向 DOM 添加一些复杂的 HTML 结构,请执行与以前相同的操作,创建一个“临时”容器,对其进行处理,然后立即将整个内容附加到 DOM。例如:

var $tmpObj = $('<div id="my-div" />').append(
$('<span class="my-title" />').text('Title 1')
).append(
$('<div class="my-description" />').append(
$('<span class="my-copy" />').text('Blah Blah Blah')
)
).on('click', function () {
alert('Don\'t Touch Me!');
}).data('my-data-key', 'my-data-val');

$('#my-div').replaceWith($tmpObj);

我喜欢使用 $.data() 存储与对象关联的数据,这样当一个元素被删除时,它就是数据,因此我们不会用无用数据占用内存.

使用 JSPerf.com,如果使用得当,它是一个了不起的工具。您可以运行测试以确定哪种方法对操作来说更快。这是我刚才设置的一个示例:http://jsperf.com/jquery-each-vs-for-loops/2

不要不必要地创建全局变量。当您这样做时,它会在查找这些变量时产生额外的开销。这一行:xmlInfo=data; 应该是 var xmlInfo=data; 除非要在 AJAX 回调函数之外访问 xmlInfo。基本上,当您在函数(或嵌套函数)内部查找全局范围内的变量时;首先,浏览器会在当前作用域中查找,然后是当前作用域的父作用域,一直到全局作用域。因此,如果您尝试在一个函数内部访问一个函数内部的全局变量,那么您现在所做的查找大约是您使用局部范围变量时的三倍。如果您必须使用全局范围的变量,请将其缓存在您的函数中并在您的函数中使用本地版本以避免额外的循环时间。

关于javascript - 动态添加/删除 HTML 时防止内存泄漏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11441755/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com