我通过ajax调用在div中加载.html文件的全部数据。 html页面包含 HTC (html组件)与页面上的元素绑定所需的链接,脚本标记。
页面的结构如下:
我正在使用jQuery来加载像这样的HTML页面
<body>
<input type="radio" class="openpage" id="0001">
<input type="radio" class="openpage" id="0002">
<input type="radio" class="openpage" id="0003">
<input type="radio" class="openpage" id="0004">
<div id="loadPage"></div>
<script>
$(document).ready(function(){
$(".openpage").on("click",function(){
$("#loadPage").load($(this).attr("id")+".html",function(){
//load a page with many htc bindings and external references
//trigger some onload functions which are not called automatically in IE
//confirmed this is in chrome
});
});
})
</script>
</body>
问题在于IE内存不断增加,因为点击单选按钮加载页面,加载几页后浏览器停止响应。 我可以在任务管理器中看到内存。
该应用程序在IE 5,6,7,8,9中运行,在IE10中以怪癖模式运行。我尝试在chrome中复制相同的场景,但没有显示任何问题。所以我认为这是IE特定的内存管理相关问题。
我阅读了很多文章,但我不相信。我也在SO上阅读了this的问题,但是它建议只加载一些在我的案例中不可接受的页面部分。这article似乎是相关的但我不确定在我的情况下究竟是什么导致内存泄漏。
上面的整个实体都是iframe 。所以作为一种解决方法,我重新加载 8页单击单选按钮后包含主页面的框架。 我试图在每次加载之前清除东西:
$("#loadPages").empty();
$("#loadPages").find("*").off();
$.ajaxSetup({ cache: false });
但没有任何作用。所以我怀疑jquery是否可以清除通过htc注册的事件。
1)如果你在这种情况下解释内存泄漏的原因会很棒。
2)一般情况下,为什么在加载许多资源后,浏览器会发生内存泄漏。这在现代浏览器中不会发生,但为什么它出现在旧浏览器中。
3)有没有办法在不刷新帧的情况下释放浏览器内存。
4)有没有办法检查所有资源都存在于浏览器内存中。
答案 0 :(得分:4)
您有几个工作流程:
从这里开始:
您的选择是:
IE为JavaScript和Rendering引擎提供了单独的COM通道,这有时意味着,特别是对于事件绑定。 JS中的对象/状态可以保持对UI / DOM节点的引用......并且DOM节点可以引用JS事件处理程序。在许多情况下,这意味着这些部分不会被垃圾收集,从而导致内存使用量增加。早期版本的情况要糟糕得多,但仍然会发生。
您可能会遇到与其他浏览器类似的问题,但IE往往会更快地显示此行为。对于长期存在的单页应用程序,情况也会更多。
如果您只将每个资源加载到其自己的DOM节点中,则可以简单地分离/重新连接该节点。此外,您可以依靠事件传播来侦听来自父节点的事件。这些都可以降低争用风险和开销。
对于取消注册事件处理程序,只要您使用jQuery注册,并使用jQuery删除/删除节点(及其子节点),jQuery就可以比大多数人更好地工作。
答案 1 :(得分:1)
你有没有考虑过使用xhr请求? 他们可以使用ajax将内容加载到目标。 我为你的问题做了一个示例小提琴。看看它。 欢呼声。
function getXmlHttpRequest() {
var xmlhttp;
if (window.XMLHttpRequest) {
xmlhttp = new XMLHttpRequest();
// code for IE7+, Firefox, Chrome, Opera, Safari
} else if (window.ActiveXObject) {
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
// code for IE5 and IE6
} else {
alert("Browser doesn't support Ajax..!!");
}
return xmlhttp;
}
function loadPage(pageTitle) {
//pageTitle = pageTitle + ".html";
xmlhttp = getXmlHttpRequest();
if (xmlhttp != null) {
xmlhttp.onreadystatechange = function() {
if (xmlhttp.readyState < 4) {
document.getElementById('loadPage').innerHTML = "Content Loading...!";
} else if (xmlhttp.readyState == 4) {
var res = xmlhttp.responseText;
document.getElementById('loadPage').innerHTML = res;
}
}
xmlhttp.open("GET", pageTitle, true);
xmlhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
xmlhttp.send(null);
}
}
function showAlert() {
alert("This is me!");
}
$(document).ready(function() {
$(".openpage").on("click", function() {
loadPage($(this).attr("id"));
});
});
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
<input type="radio" class="openpage" name="radio-group" id="https://dl.dropboxusercontent.com/u/105580681/xhr-fiddle/0001.html">
<input type="radio" class="openpage" name="radio-group" id="https://dl.dropboxusercontent.com/u/105580681/xhr-fiddle/0002.html">
<input type="radio" class="openpage" name="radio-group" id="https://dl.dropboxusercontent.com/u/105580681/xhr-fiddle/0003.html">
<input type="radio" class="openpage" name="radio-group" id="https://dl.dropboxusercontent.com/u/105580681/xhr-fiddle/0004.html">
<div id="loadPage"></div>
&#13;
在这个小提琴中,我使用Dropbox链接加载html文件。您可以使用0001 - 0004 id号的初始概念。
但是,如果要加载html页面的整个内容,这将加载从外部html页面到目标主页面内部的所有内容。
例如:
<div id="loadPage">
<title>TODO supply a title</title>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<div>Content of HTML 0001 Page</div>
</div>
这会影响主页面的DOM文件。页面功能不会松动,但它不是一个好的编程技术。因此,您可能需要在要在目标元素上显示的xxxx.html文件中编写或加载内容。
了解更多信息
Using XMLHttpRequest Mozilla MDN
Using FormData Objects Mozilla MDN