关于ie6的DOM JScript内存泄漏介绍

ie6的js实现是基于JScript和DOM ActiveX各种分离部件实现的,所以回收内存自然有些问题,下面简单介绍下内存泄漏
例一
Js代码
  1. <html>  
  2.     <head><title>Queue Test 2</title>  
  3.     </head>  
  4.     <body>  
  5.         <script>  
  6.             /*global setTimeout */  
  7.             (function (limit, delay) {  
  8.                 var queue = new Array(10);  
  9.                 var n = 0;  
  10.   
  11.                 function makeSpan(n) {  
  12.                     var s = document.createElement('span');  
  13.                     document.body.appendChild(s);  
  14.                     var t = document.createTextNode(' ' + n);  
  15.                     s.appendChild(t);  
  16.                     return s;  
  17.                 }  
  18.   
  19.                 function process(n) {  
  20.                     queue.push(makeSpan(n));  
  21.                     var s = queue.shift();  
  22.                     if (s) {  
  23.                         s.parentNode.removeChild(s);  
  24.                     }  
  25.                 }  
  26.   
  27.                 function loop() {  
  28.                     if (n < limit) {  
  29.                         process(n);  
  30.                         n += 1;  
  31.                         setTimeout(loop, delay);  
  32.                     }  
  33.                 }  
  34.   
  35.                 loop();  
  36.             })(10000, 10);  
  37.         </script>  
  38.     </body>  
  39. </html>  
<html>
    <head><title>Queue Test 2</title>
    </head>
    <body>
        <script>
            /*global setTimeout */
            (function (limit, delay) {
                var queue = new Array(10);
                var n = 0;

                function makeSpan(n) {
                    var s = document.createElement('span');
                    document.body.appendChild(s);
                    var t = document.createTextNode(' ' + n);
                    s.appendChild(t);
                    return s;
                }

                function process(n) {
                    queue.push(makeSpan(n));
                    var s = queue.shift();
                    if (s) {
                        s.parentNode.removeChild(s);
                    }
                }

                function loop() {
                    if (n < limit) {
                        process(n);
                        n += 1;
                        setTimeout(loop, delay);
                    }
                }

                loop();
            })(10000, 10);
        </script>
    </body>
</html>

在ie6上面执行毫无问题,没有泄露,最多10个span,多了就remove,DOM和JScript没有交叉

例二

Js代码
  1. <html>  
  2.     <head><title>Queue Test 2</title>  
  3.     </head>  
  4.     <body>  
  5.   
  6.         <script>  
  7.             /*global setTimeout */  
  8.             (function (limit, delay) {  
  9.                 var queue = new Array(10);  
  10.                 var n = 0;  
  11.   
  12.                 function makeSpan(n) {  
  13.                     var s = document.createElement('span');  
  14.                     document.body.appendChild(s);  
  15.                     var t = document.createTextNode(' ' + n);  
  16.                     s.appendChild(t);  
  17.                     s.onclick = function (e) {  
  18.                         s.style.backgroundColor = 'red';  
  19.                         alert(n);  
  20.                     };  
  21.                     return s;  
  22.                 }  
  23.   
  24.                 function process(n) {  
  25.                     queue.push(makeSpan(n));  
  26.                     var s = queue.shift();  
  27.                     if (s) {  
  28.                         s.parentNode.removeChild(s);  
  29.                     }  
  30.                 }  
  31.   
  32.                 function loop() {  
  33.                     if (n < limit) {  
  34.                         process(n);  
  35.                         n += 1;  
  36.                         setTimeout(loop, delay);  
  37.                     }  
  38.                 }  
  39.   
  40.                 loop();  
  41.             })(10000, 10);  
  42.         </script>  
  43.     </body>  
  44. </html>  
<html>
    <head><title>Queue Test 2</title>
    </head>
    <body>

        <script>
            /*global setTimeout */
            (function (limit, delay) {
                var queue = new Array(10);
                var n = 0;

                function makeSpan(n) {
                    var s = document.createElement('span');
                    document.body.appendChild(s);
                    var t = document.createTextNode(' ' + n);
                    s.appendChild(t);
                    s.onclick = function (e) {
                        s.style.backgroundColor = 'red';
                        alert(n);
                    };
                    return s;
                }

                function process(n) {
                    queue.push(makeSpan(n));
                    var s = queue.shift();
                    if (s) {
                        s.parentNode.removeChild(s);
                    }
                }

                function loop() {
                    if (n < limit) {
                        process(n);
                        n += 1;
                        setTimeout(loop, delay);
                    }
                }

                loop();
            })(10000, 10);
        </script>
    </body>
</html>

执行时候,打开任务管理器,大概每秒PF上升1M,原因是DOM元素span握有带closure的匿名函数,导致匿名函数空间不能释放

例三
Js代码
  1. <html>  
  2.     <head><title>Queue Test 2</title>  
  3.     </head>  
  4.     <body>  
  5.         <p>  
  6.             Queue Test 2 adds an event handler to each span. See <a href="http://www.crockford.com/javascript/memory/leak.html">http://www.crockford.com/javascript/memory/leak.html</a>  
  7.         </p>  
  8.         <script>  
  9.             /*global setTimeout */  
  10.             (function (limit, delay) {  
  11.                 var queue = new Array(10);  
  12.                 var n = 0;  
  13.   
  14.                 function makeSpan(n) {  
  15.                     var s = document.createElement('span');  
  16.                     document.body.appendChild(s);  
  17.                     var t = document.createTextNode(' ' + n);  
  18.                     s.appendChild(t);  
  19.                     s.onclick = function (e) {  
  20.                         s.style.backgroundColor = 'red';  
  21.                         alert(n);  
  22.                     };  
  23.                     return s;  
  24.                 }  
  25.   
  26.                 function process(n) {  
  27.                     queue.push(makeSpan(n));  
  28.                     var s = queue.shift();  
  29.                     if (s) {  
  30.                     s.οnclick=null;  
  31.                         s.parentNode.removeChild(s);  
  32.                     }  
  33.                 }  
  34.   
  35.                 function loop() {  
  36.                     if (n < limit) {  
  37.                         process(n);  
  38.                         n += 1;  
  39.                         setTimeout(loop, delay);  
  40.                     }  
  41.                 }  
  42.   
  43.                 loop();  
  44.             })(10000, 10);  
  45.         </script>  
  46.     </body>  
  47. </html>  
<html>
    <head><title>Queue Test 2</title>
    </head>
    <body>
        <p>
            Queue Test 2 adds an event handler to each span. See <a href="http://www.crockford.com/javascript/memory/leak.html">http://www.crockford.com/javascript/memory/leak.html</a>
        </p>
        <script>
            /*global setTimeout */
            (function (limit, delay) {
                var queue = new Array(10);
                var n = 0;

                function makeSpan(n) {
                    var s = document.createElement('span');
                    document.body.appendChild(s);
                    var t = document.createTextNode(' ' + n);
                    s.appendChild(t);
                    s.onclick = function (e) {
                        s.style.backgroundColor = 'red';
                        alert(n);
                    };
                    return s;
                }

                function process(n) {
                    queue.push(makeSpan(n));
                    var s = queue.shift();
                    if (s) {
					s.οnclick=null;
                        s.parentNode.removeChild(s);
                    }
                }

                function loop() {
                    if (n < limit) {
                        process(n);
                        n += 1;
                        setTimeout(loop, delay);
                    }
                }

                loop();
            })(10000, 10);
        </script>
    </body>
</html>

手动将带closure的匿名函数null后,再remove,内存无泄漏,最后有一purge函数,为Douglas Crockford所写
Js代码
  1. function purge(d) {  
  2.     var a = d.attributes, i, l, n;  
  3.     if (a) {        l = a.length;  
  4.         for (i = 0; i < l; i += 1) {  
  5.             n = a[i].name;  
  6.             if (typeof d[n] === 'function') {  
  7.                 d[n] = null;  
  8.             }  
  9.         }  
  10.     }  
  11.     a = d.childNodes;  
  12.     if (a) {  
  13.         l = a.length;  
  14.         for (i = 0; i < l; i += 1) {  
  15.             purge(d.childNodes[i]);  
  16.         }  
  17.     }  
  18. }  
function purge(d) {
    var a = d.attributes, i, l, n;
    if (a) {        l = a.length;
        for (i = 0; i < l; i += 1) {
            n = a[i].name;
            if (typeof d[n] === 'function') {
                d[n] = null;
            }
        }
    }
    a = d.childNodes;
    if (a) {
        l = a.length;
        for (i = 0; i < l; i += 1) {
            purge(d.childNodes[i]);
        }
    }
}

入门介绍帖,很可能在ie6打完hotfix后测试结果不一样
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值