Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/jquery/70.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Jquery 使用ajax加载html内容。浏览器不会释放内存_Jquery_Asp.net_Ajax_Browser_Memory Leaks - Fatal编程技术网

Jquery 使用ajax加载html内容。浏览器不会释放内存

Jquery 使用ajax加载html内容。浏览器不会释放内存,jquery,asp.net,ajax,browser,memory-leaks,Jquery,Asp.net,Ajax,Browser,Memory Leaks,我们有一个单页应用程序,它通过对不同web服务的ajax调用加载所有内容。起始页只加载一次,然后根据用户操作,使用我们在服务器上预呈现的html包更新不同的容器 现在,当应用程序长时间运行而不重新启动时,我们发现了一个问题。浏览器和计算机开始变慢,响应速度变慢。 在任务管理器中查看该进程时,可以发现它作为浏览器进程会消耗大量内存。这个过程并没有释放内存 我开始研究这个问题,在设置一个示例应用程序时,我发现了一个我想知道的效果。 该应用程序很简单,由一个web服务方法、一个aspx页面和一个jav

我们有一个单页应用程序,它通过对不同web服务的ajax调用加载所有内容。起始页只加载一次,然后根据用户操作,使用我们在服务器上预呈现的html包更新不同的容器

现在,当应用程序长时间运行而不重新启动时,我们发现了一个问题。浏览器和计算机开始变慢,响应速度变慢。 在任务管理器中查看该进程时,可以发现它作为浏览器进程会消耗大量内存。这个过程并没有释放内存

我开始研究这个问题,在设置一个示例应用程序时,我发现了一个我想知道的效果。 该应用程序很简单,由一个web服务方法、一个aspx页面和一个javascript文件组成

这是代码

网络服务:

public class WebService1 : WebService
{

    [WebMethod]
    public string GetData()
    {
        var returnValue = "";

        var webRequest = WebRequest.Create("http://www.w3schools.com/");
        var webResponse = webRequest.GetResponse();
        var responseStream = webResponse.GetResponseStream();
        if (responseStream != null)
        {
            using(var streamReader = new StreamReader(responseStream))
            {
                returnValue = streamReader.ReadToEnd();
                var startBody = returnValue.IndexOf("<body>") + "<body>".Length;
                var endBody = returnValue.IndexOf("</body>");
                returnValue = returnValue.Substring(startBody, endBody - startBody);
            }
        }
        return returnValue;
    }
}
今天,我们对web服务的所有调用都是使用asp.net scriptmanager ajax框架完成的。但是,如果您运行这个测试应用程序,您可以看到使用jQueryAjax和asp.NETAjax获取数据之间的一些不同行为,至少在IE9中是这样。Chrome似乎是平等的,但在IE9中,当您使用jQuery获取数据时,它不会消耗那么多内存,但在另一种情况下,使用asp.net ajax时,它会增长,并且永远不会释放内存

我这里有几个问题。首先,有什么区别?使用asp.net ajax时是否存在性能损失?第二,我的javascript代码中是否存在内存泄漏?在一个简化的示例中,这通常是我们在整个应用程序中使用的模式。如果有什么问题,我们需要知道并纠正它。 这种内存消耗可能是问题的原因吗?我的开发人员计算机中有很多内存,所以浏览器可能永远不会释放内存,因为它不需要释放内存?也许这是虚惊一场,而问题是别的。 当浏览器看起来没有响应时,通常的原因是CPU过高,但这里的情况并非如此


感谢对这个问题的任何帮助或新观点。谢谢。

我想我终于找到了这个问题的答案

IE9不支持javascript函数eval():

他们推荐一些解决方法,其中之一是在处理JSON反序列化时使用JSON.parse

我们在aspx页面中使用Ajax控制工具包Scriptmanager。 但是,如果您调查它在内部自动生成的js代码中做了什么,您可以看到以下代码块:

Sys.Serialization.JavaScriptSerializer.deserialize = function Sys$Serialization$JavaScriptSerializer$deserialize(data, secure) {
    /// <summary locid="M:J#Sys.Serialization.JavaScriptSerializer.deserialize" />
    /// <param name="data" type="String"></param>
    /// <param name="secure" type="Boolean" optional="true"></param>
    /// <returns></returns>
    var e = Function._validateParams(arguments, [
        {name: "data", type: String},
        {name: "secure", type: Boolean, optional: true}
    ]);
    if (e) throw e;

    if (data.length === 0) throw Error.argument('data', Sys.Res.cannotDeserializeEmptyString);
    try {    
        var exp = data.replace(Sys.Serialization.JavaScriptSerializer._dateRegEx, "$1new Date($2)");

        if (secure && Sys.Serialization.JavaScriptSerializer._jsonRegEx.test(
             exp.replace(Sys.Serialization.JavaScriptSerializer._jsonStringRegEx, ''))) throw null;
        return eval('(' + exp + ')');
    }
    catch (e) {
         throw Error.argument('data', Sys.Res.cannotDeserializeInvalidJson);
    }
}
Sys.Serialization.JavaScriptSerializer.deserialize=函数Sys$Serialization$JavaScriptSerializer$deserialize(数据,安全){
/// 
/// 
/// 
/// 
var e=函数。\u验证图(参数[
{name:“data”,类型:String},
{name:“secure”,类型:Boolean,可选:true}
]);
如果(e)抛出e;
if(data.length==0)抛出Error.argument('data',Sys.Res.cannotDeserializeEmptyString);
试试{
var exp=data.replace(Sys.Serialization.JavaScriptSerializer._dateRegEx,“$1新日期($2)”);
if(secure&&Sys.Serialization.JavaScriptSerializer.\u jsonRegEx.test(
exp.replace(Sys.Serialization.JavaScriptSerializer.\u jsonStringRegEx',))抛出null;
返回值(“(“+exp+”)”);
}
捕获(e){
抛出错误。参数('data',Sys.Res.cannotDeserializeInvalidJson);
}
}
我相信这就是问题的原因,我的选择是使用jquery$.ajax


我希望这能帮助那些在IE9中遇到同样内存问题的人。

你在不同的浏览器中测试过吗?您是否看到它们中的许多内存使用量增加了?如果您可以将其缩小到单个浏览器,则可能是浏览器内存泄漏,而不是与您的应用程序有关。附带说明:您可能希望使用setInterval而不是setTimeout,因为您似乎希望每2秒重复从服务器获取数据。此外,您可能希望将内容清除代码移动到ajax响应处理程序中,这样用户就不会在请求和响应之间看到空内容。最后,您需要小心单击处理程序中的超时代码。如果用户在T 0毫秒时单击,然后在T 50毫秒时再次单击,则您将通过设置超时在T 2000毫秒和T 2050毫秒时重新加载内容。您可能想清除超时。这只是一个测试应用程序。我所说的“这通常是我们在整个应用程序中使用的模式”是指我们调用Web服务的方式。在测试应用程序中,这里的目的只是单击一次其中一个按钮来创建一个循环。我还从html中清除容器,以查看实际发生的事情。我们在应用程序中不这样做。是的,谷歌chrome和ie9都存在这个问题。
$(document).ready(function () {

$('#getDataJquery').click(function () {
    getDataWithJQuery();
    setTimeout(function () {
        $('#container').html('');
        $('#getDataJquery').trigger('click');
    }, 2000);
});

$('#getDataAspnet').click(function () {
    getDataWithAspnet();
    setTimeout(function () {
        $('#container').html('');
        $('#getDataAspnet').trigger('click');
    }, 2000);
});

});

function getDataWithJQuery() {
    $.ajax({
        url: 'WebService1.asmx/GetData',
        type: 'POST',
        dataType: 'json',
        success: jQueryResponse,
        contentType: 'application/json'
    }
);
}

function getDataWithAspnet() {
    AjaxJqueryVsAspNet.WebService1.GetData(aspnetResponse);
}

function jQueryResponse(response) {
    loadHtml(response.d);
}

function aspnetResponse(response) {
    loadHtml(response);
}

function loadHtml(html) {
    $('#container').html(html);
}
Sys.Serialization.JavaScriptSerializer.deserialize = function Sys$Serialization$JavaScriptSerializer$deserialize(data, secure) {
    /// <summary locid="M:J#Sys.Serialization.JavaScriptSerializer.deserialize" />
    /// <param name="data" type="String"></param>
    /// <param name="secure" type="Boolean" optional="true"></param>
    /// <returns></returns>
    var e = Function._validateParams(arguments, [
        {name: "data", type: String},
        {name: "secure", type: Boolean, optional: true}
    ]);
    if (e) throw e;

    if (data.length === 0) throw Error.argument('data', Sys.Res.cannotDeserializeEmptyString);
    try {    
        var exp = data.replace(Sys.Serialization.JavaScriptSerializer._dateRegEx, "$1new Date($2)");

        if (secure && Sys.Serialization.JavaScriptSerializer._jsonRegEx.test(
             exp.replace(Sys.Serialization.JavaScriptSerializer._jsonStringRegEx, ''))) throw null;
        return eval('(' + exp + ')');
    }
    catch (e) {
         throw Error.argument('data', Sys.Res.cannotDeserializeInvalidJson);
    }
}