循环引用如何导致JavaScript中的内存泄漏?

循环引用

 当两个变量通过给每个对象赋予一个引用计数为1时,便形成了循环引用。在纯垃圾收集系统中,当所涉及的变量没有引用时,循环引用可能不是问题。声明的变量将被垃圾回收。在引用计数系统中,两个对象都不会被销毁,因为引用计数不能为零。

在使用引用计数和垃圾回收的混合系统中,由于系统无法识别循环引用,因此将发生内存泄漏。

示例

下面的示例显示了javascript对象和DOM对象之间的循环引用。javascript对象通过“ expando”属性引用了DOM对象(Div)和Dom对象(Div),引用了javascript对象(obj)。由于两个对象都互相引用,因此不会导致内存泄漏而将其破坏。

<html>
<body>
<script>  
   window.onload = function(){
   var obj=document.getElementById("DivElement");
   document.getElementById("DivElement").expandoProperty=obj;
   obj.String=new Array(1000).join(new Array(2000);
   };
</script>
</body>
</html>

避免内存泄漏

在下面的示例中,最初的javascript对象和DOM对象都是循环引用,但是当为javascript对象分配null时,这两个对象(javascript和DOM对象)将陷入困境,以找出它们所引用的对象,即javascript对象是否正在引用null或DOM对象(通过破坏循环引用)。 

示例

<html>
<body>
<script>  
   window.onload = function(){
   var obj=document.getElementById("DivElement");
   document.getElementById("DivElement").expandoProperty=obj;
   obj.String=new Array(1000).join(new Array(2000);
   obj = null        // this breaks circular reference
   };
</script>
</body>
</html>