JavaScript闭包的理解

理解闭包关键是理解JS的对象的本质以及垃圾收集机制。函数也是对象,也有属性,通常执行一个函数时,局部变量在函数执行完后,内存会被回收,这是JS的垃圾收集机制决定的,如果想保存局部变量所占用的内存,就必须把保存在另一个不被回收的变量中,通常是全局变量。函数在创建时,内部属性[[Scope]]保存了作用域链,作用域链中包含外部函数以及全局对象的变量,被称为变量对象。所以把内部函数返回时,由于把函数保存了,所以内部属性[[Scope]]所保存的变量对象也就保存了而没有被回收,因此局部变量也就被保存了。
最简单的闭包:

function f1() {
    var i = 0;
    return function () {
        var j = 0;
        i++;
        console.log(i,j);
    };
}
var fn = f1();
fn();//1 0
fn();//2 0

还有诸如给元素添加事件,事件函数保存着外部函数的变量,通过这个特性可以让按钮显示被点击次数。
当然可以创建多层闭包,最内部函数保存所有外部函数以及全局对象的变量,但并不是任何地方都用闭包,因为其始终都带有[[Scope]]属性,所有比较占内存,所以在需要的时候才用。
闭包在模块化编程,为函数或对象创建私有变量的时候非常有用,可以避免全局污染以及变量命名冲突的问题。
值得注意的是因为[[Scope]]与函数有关,如上述例子,在两次执行f1函数把返回的函数保存在不同的变量中,其外部函数的变量是互不影响的。如:

function f1() {
    var i = 0;
    return function () {
        var j = 0;
        i++;
        console.log(i,j);
    };
}
var fn = f1();
fn();//1 0
fn();//2 0
var fn1 = f1();
fn1();//1 0
fn(); //3 0
fn1();//2 0
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值