[JS]遭遇IE内存泄漏

以前因为没有做过比较大型的应用,所以也一直没注意这些。最近的一个项目里需要频繁的创建和清除一批对象,导致IE占用的实际内存和虚拟内存急剧上升,而且最小化IE窗口或关闭窗口也不会释放。搜索了一下关于IE内存泄漏的文章,其中birdshome上的这一系列文章讲的比较全面,引起IE内存泄漏的主要情况为js对象实例跟dom对象的相互引用、“内部函数引用(Closures)”以及DOM插入顺序泄漏。

以前为了方便,在涉及操作dom对象的地方,通常建立一个对dom对象的引用,dom对象也建立一个指向js对象实例的引用,例如:
function myObject()
{
this.element = document.getElementById(‘myElement’);
document.getElementById(‘myElement’).instance = this;
}

var obj = new myObject();

这样不管js调用dom还是从dom反向找到实例都非常方便,但如果在对象销毁或document unload的时候不去解除他们之间的引用,就会引起内存泄漏。所以应该尽量避免这种写法,通过在对象中指定dom对象的id或者其他方式来建立js对象跟dom对象的关联。

所谓“内部函数引用(Closures)“,这里有详细的解释。而对于dom插入顺序泄漏这个就很难让人理解了,只能尽量遵循这个规则。

关于内存回收,同样引用birdshome上对于bindows对象dispose方法的解释:切断DHTML对象实例和脚本对象实例的引用链;清除全局cache变量中的数据,使用delete关键字;使用attachEvent方式导入的事件处理函数,需要detach;其它事件处理回调,使用赋null的方式清空;切断脚本对象之间的parent或child关系引用链。

还有就是尽量不要使用IE透明滤镜,我发现当插入一个长宽各为1000px并应用透明滤镜的div时,内存占用增加大约4MB。

*日志发出去好久才发现有错字,是“泄漏”而不是“泄露”。

6 Comments »

  1. crazysoul said,

    October 31, 2006 @ 12:39 pm

    滤镜渲染占用内存多不是大问题,而如果用变量引用了这个滤镜的ELEMENT OBJECT,经过一系列的处理后引起类似闭包那样的内存泄露,用户离开网站后内存资源得不到释放,那就严重影响用户对网站的观感了(虽然90%的用户不知道他们的IE内存占用是怎么膨胀起来的)

  2. legend said,

    October 31, 2006 @ 2:21 pm

    看来滤镜用起来得小心了。

  3. phzzy said,

    December 1, 2006 @ 5:00 pm

    想问个 JS 编码的问题…

    http://hi.baidu.com/%E7%99%BE%E5%BA%A6%E6%90%9C%E8%97%8F/rss
    http://hi.baidu.com/%B0%D9%B6%C8%CB%D1%B2%D8/rss

    这两个地址,都是
    http://hi.baidu.com/百度空间/rss
    经过编码后的结果,我想问,如果用户在网站上输入以上这两个地址,我怎么得知他给的地址是用的 gb2312 编码还是 utf-8 编码?
    判断不了的话,用JS解不出数据,郁闷…

  4. phzzy said,

    December 1, 2006 @ 5:05 pm

    JS 自己是说可以回收内存的,但在这种闭环情况下,回收好像有错误。还有 for 循环,据说效率比较低。还有操作 dom 时,卡得要死,嘿。。。

  5. legend said,

    December 3, 2006 @ 9:03 am

    urldecode后再判断编码吧。

  6. 网络 said,

    July 26, 2007 @ 9:29 pm

    for 循环,效率比较低,同感…

RSS feed for comments on this post

Leave a Comment