如果在函数内部生命函数inner,然后在函数外部调用inner,这个过程即产生了一个闭包。
闭包的用途:
1、匿名自执行函数,类似:click(function(){})。
2、缓存。
3、实现封装。闭包的的一个重要用途就是实现面向对象中的对象。传统的对象语言都提供类的模板机制,这样不同的对象就拥有了独立的成员和状态,互不干涉。
虽然JavaScript没有这种机制,但是我们可以使用闭包实现该机制,如下程序:
//JavaScript是基于对象而非面向对象的,若想实现面向对象,则需要使用闭包
function Person()
{
var name='default';
return {
getName:function()
{
return name;
},
setName:function(newName)
{
name=newName;
}
};
};
var jake=Person();
alert(jake.getName());
jake.setName('jake');
alert(jake.getName());
var jay=Person();
alert(jay.getName());
jay.setName('jay');
alert(jay.getName());
应该注意的问题:
1、内存泄漏,JavaScript解释器都具备垃圾回收机制,一般采用的是引用计数的形式,如果一个对象的引用计数为0,则垃圾回收器会将其回收,这个过程是自动的。
但是有了闭包后,变量的应用将变的比较复杂,因为局部变量肯能会在某个时刻被外部应用,如果再出现嵌套引用等情况,则会出现无法回收的泄漏。
2、上下文引用this,它表示的是调用对象的引用,而在闭包中,最容易出现错误的地方就是误用this。虽然闭包可以引用局部变量,但是涉及到this的时候,情况就不对了,
如下例:
//闭包中this变量的使用
function aa()
{
var obj=document.getElementById('name');
this.value='1000';//此处的this表示调用的对象
obj.οnclick=function()
{
alert("触发该事件的对象this:"+this.value);//此处的this其实是本方法的触发对象obj,而并非上一句中的this,故其值也非1000
};
//解决闭包的局部this引用问题
var self=this;
obj.οnmοuseοver=function()
{
alert("局部变量的this:"+self.value);
};
}
aa();//如果在这里执行调用对象就是window
alert(window.value);