JS闭包,以及适用场景

闭包的定义

不用解释了,网上到处都是。简单的说:一个定义在函数内部的函数与包含它的外部函数构成了闭包,内部函数可以访问外部函数的变量,这些变量将一直保存在内存中,直到无法再引用这个内部函数

举个例子:

var vvval = 0;
function outerFun(i) {
    var vval = i;
    function innerFun() {
        var val = i;
        console.log("内部变量:"+val);
        console.log("外部变量:"+vval);
        console.log("全局变量:"+vvval);
        val++;
        vval++;
        vvval++;
    }
    return innerFun;
}
var testFun1 = outerFun(10);
testFun1();//内部变量:10 外部变量:10 全局变量:0
testFun1();//内部变量:10 外部变量:11 全局变量:1
var testFun2 = outerFun(20);
testFun2();//内部变量:20 外部变量:20 全局变量:2
testFun2();//内部变量:20 外部变量:21 全局变量:3

结论:
    val是innerFun()的局部变量,每次执行innerFun()都会重新赋值;
    vval是innerFun()的上一级变量,每次执行innerFun()的结果会保存在内存中,是outerFun()的局部变量,每次执行outerFun()都会重新赋值;
    vvval是innerFun()的上上一级变量,每次执行innerFun()的结果会保存在内存中,是outerFun()的上一级变量,每次执行outerFun()的结果会保存在内存中;
    
在JavaScript中,作用域只有全局作用域和函数级作用域两种,在下一级作用域中可以访问和修改上一级作用域的变量,在定义函数时,JS会自动维护一个作用域链,当前的局部作用域位于作用域链顶端,并可以依次向上回溯。闭包的实质就是延长了作用域链。

再举一个例子:

//若已经定义了10个<div>,现在想用循环给每个<div>根据序号绑定不同的事件
var i;
for(i=0;i<10;i++) {
    $("div:eq("+i+")").on("click",function() {
        console.log(i);
    });
}

然而,点击每个<div>输出结果均为10,这是因为i是全局变量,当改变i的值时,所有引用了它的函数都会受到影响。这时我们可以通过延长作用域链,为i的值保存一个副本,使它们之间不会互相影响:

var i;
for(i=0;i<10;i++) {
    function outer() {
        var vval = i;
        function inner() {
            console.log(vval);
        }
        $("div:eq("+vval+")").on("click",inner);
    }
    outer();
}

每循环一次就定义了一个外部函数outer()和一个内部函数inner(),因为inner()被绑定在<div>的click事件上,所以outer()中的变量没有在执行完之后就被释放,而是保存在内存中,最后需要执行一次outer(),初始化变量vval,当然你也可以使用自执行的匿名函数代替outer()。
解释一下:在JS中函数是可以重复定义的,只是执行的是最后一次定义的函数而已,例如:

function a() {
    console.log(1);
}
a();
function a() {
    console.log(2);
}
a();
//输出两个2
时间: 2024-10-07 02:42:11

JS闭包,以及适用场景的相关文章

js闭包之应用场景

闭包的解释 一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分.闭包是指有权访问另一个函数作用域的变量的函数 在javascript中,只有函数内部的子函数才能读取局部变量,所以说,闭包可以简单理解成"定义在一个函数内部的函数".所以,在本质上,闭包是将函数内部和函数外部连接起来的桥梁. 闭包的特点: 1) 作为一个函数变量的一个引用,当函数返回时,其处于激活状态. 2) 一个闭包就是当一个函数返回时,一个没有释放资源的栈区. 简单的说,

javascript深入理解js闭包

一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 function f1(){ var n=999; } alert(n); // error 这里有一个地方需要注意,函数

深入理解js闭包

闭包(closure)是Javascript语言的一个难点,也是它的特色,很多高级应用都要依靠闭包实现. 一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 function

javascript深入理解js闭包(摘自网络)

闭包(closure)是Javascript语言的一个难点,也是它的特色,很多高级应用都要依靠闭包实现. 一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 function

js闭包的作用

js闭包的用途详解 js闭包可以用在许多地方.它的最大用处有两个,一个是前面提到的可以读取函数内部的变量,另一个就是让这些变量的值始终保持在内存中.具体怎么理解呢,各位看官请仔细看好下文 我们来看看闭包的用途.事实上,通过使用闭包,我们可以做很多事情.比如模拟面向对象的代码风格:更优雅,更简洁的表达出代码:在某些方面提升代码的执行效率. 1 匿名自执行函数 我们知道所有的变量,如果不加上var关键字,则默认的会添加到全局对象的属性上去,这样的临时变量加入全局对象有很多坏处,比如:别的函数可能误用

(转)javascript深入理解js闭包

一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 function f1(){ var n=999; } alert(n); // error 这里有一个地方需要注意,函数

关于JS闭包,作者不详(转)

说明:本文由两篇文章结合而成,系从他人笔记中转过来的, 具体作者不详.因为觉得不错,遂共享之.如有侵权,立删致歉. 一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 fun

js闭包的理解

闭包的两个特点: 1.作为一个函数变量的一个引用 , 当函数返回时,其处于激活状态. 2.一个闭包就是当一个函数返回时,一个没有释放资源的栈区. 其实上面两点可以合成一点,就是闭包函数返回时,该函数内部变量处于激活状态,函数所在栈区依然保留. 我们所熟知的主流语言,像C,java等,在函数内部只要执行了return,函数就会返回结果,然后内存中删除该函数所在的区域.生命周期也就停止了.一般的js函数也是这样. 但是有闭包特性的js函数有点特殊. 就例子来说: function a(){ var

非常直白的 js 闭包概念.&lt;转载&gt;

(转载:http://www.felixwoo.com/archives/247) 一.什么是闭包? 官方"的解释是:闭包是一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分.相信很少有人能直接看懂这句话,因为他描述的太学术.其实这句话通俗的来说就是:JavaScript中所有的function都是一个闭包.不过一般来说,嵌套的function所产生的闭包更为强大,也是大部分时候我们所谓的"闭包".看下面这段代码: functi

javascript深入理解js闭包(个人理解,大神勿喷)

一.变量的作用域 要理解闭包,首先必须理解Javascript特殊的变量作用域. 变量的作用域无非就是两种:全局变量和局部变量. Javascript语言的特殊之处,就在于函数内部可以直接读取全局变量. Js代码 var n=999; function f1(){ alert(n); } f1(); // 999 另一方面,在函数外部自然无法读取函数内的局部变量. Js代码 function f1(){ var n=999; } alert(n); // error 这里有一个地方需要注意,函数