11

我试图弄清楚为什么 IE 在将 AJAX 请求的 HTML 页面包装在 jQuery 对象中进行处理时会泄漏内存。用户可能会访问页面并让它停留几分钟或几小时,因此页面ajax每分钟使用几次 jQuery 的方法来获取新数据,然后我将页面的重要部分替换为新的预渲染数据。

在这一点上,我已将其缩小到一个调用 - 当$(data)调用包装 HTML 字符串时,内存会出现一点峰值,并且似乎从来没有被垃圾收集。随着时间的推移,使用了数百 MB,我被迫重新加载页面或重新启动 IE。

这个小提琴能够重现这个问题。它使用 AJAX 请求页面,然后$(data)在紧密循环中调用以夸大泄漏。Chrome 和 Firefox 似乎都像我预期的那样做出反应(内存被回收),但 IE 表现不佳。惊喜。

使用 Process Explorer,我发现在运行上述小提琴两次后内存消耗急剧增加。

在此处输入图像描述

我目前在标准模式下使用 IE9。

为什么会这样?有解决方法吗?

更新

这是一个在不使用 AJAX 的情况下演示该问题的小提琴。

4

2 回答 2

3

我找到了解决上述问题的方法。

在解决这个问题时,我尝试了各种方法来防止泄漏发生。我想出的解决方案是放弃使用$.ajax来检索数据并$()包装结果。相反,我使用$('#destination').load('sourceUrl #selector')(参见文档)将数据推送到隐藏的 div 中,然后以这种方式操作结果。

结果是在幕后$.load使用$.parseHTML来操纵结果并将它们推到指定的位置($()显然没有)。有关源代码行,请参见此处

  • $(htmlText)泄漏
  • $(bodyText)不泄漏
  • $.parseHtml(htmlText)慢慢泄漏(?)
  • $.parseHtml(bodyText)不泄漏

这是一个要演示的小提琴。

我不知道为什么它的行为方式如此,但它的短处似乎是:尽可能避免解析完整的 HTML 文档。

于 2013-03-18T17:56:33.997 回答
0

我看到了您所看到的,当我更改代码以在每次调用成功时重新分配函数时,神奇地它没有泄漏(至少在我的环境中。)

所以,我的解决方案很愚蠢,但它似乎对我有用。对你起作用吗?

$(function(){
    $.ajaxSetup({ cache: false });

    $('#go').click(performCall);
});

function performCall() {
    $('#timestamp').text('Working...');

    $.ajax({
       url: 'http://fiddle.jshell.net/',
        success: function(){
            var func = function(data, textStatus, jqXHR) {
                $('#timestamp').text('Done at ' + new Date());
                for(var x = 0; x < 100; x++) {
                    var $a = $(data);
                }
            };
            func();
        }
   });
}

http://jsfiddle.net/tCvUw/

于 2013-03-14T18:44:32.193 回答