• JavaScript中闭包的概念、原理、作用及应用


    一、闭包概念

    闭包:有权访问另一个函数作用域中的变量的函数;一般情况就是在一个函数中包含另一个函数。

    从官方定义我们知道闭包是一个函数,只不过这个函数有[超能力],可以访问到另一个函数的作用域。

    为什么说这个叫做[超能力]呢?

    因为我们知道函数作用域是独立的、封闭的,外部的执行环境是访问不了的,但是闭包具有这个能力和权限。

    那闭包是怎样的一个表现形式呢?

    第一,闭包是一个函数,而且存在于另一个函数当中

    第二,闭包可以访问到父级函数的变量,且该变量不会销毁

    function person(){
        var name = '有鱼';
        function cat(){
            console.log(name);
        }
        return cat;
    }
    var per = person();// per的值就是return后的结果,即cat函数
    per();// 有鱼 per()就相当于cat()
    per();// 有鱼 同上,而且变量name没有销毁,一直存在内存中,供函数cat调用
    per();// 有鱼

    二、闭包原理

    闭包的实现原理,其实是利用了作用域链的特性,我们都知道作用域链就是在当前执行环境下访问某个变量时,如果不存在就一直向外层寻找,最终寻找到最外层也就是全局作用域,这样就形成了一个链条。

    例如:

    var age = 18;
    function cat(){
        age++;
        console.log(age);// cat函数内输出age,该作用域没有,则向外层寻找,结果找到了,输出[19];
    }
    cat();//19

    看到这里,大家都会说这不就是最简单的函数和变量形式吗?闭包在哪里?别急,我们接着往下看:

    如果我们再次调用时,结果会一直增加,也就变量age的值一直递增。

    cat();//20
    cat();//21
    cat();//22

    如果程序还有其他函数,也需要用到age的值,则会受到影响,而且全局变量还容易被人修改,比较不安全,这就是全局变量容易污染的原因,所以我们必须解决变量污染问题,那就是把变量封装到函数内,让它成为局部变量。

    function person(){
        var age = 18;
        function cat(){
            age++;
            console.log(age);
        }
        return cat;
    }
    person();// 19
    person();// 19

    这里又出现问题了,每次调用函数person,进入该作用域,变量age就会重新赋值为18,所以cat的值一直是19;所以需要做一下调整:

    var per = person();//per相当于函数cat
    per();// 19 即cat() 这样每次调用不在经过age的初始值,这样就可以一直增加了
    per();// 20
    per();// 21

    而且变量age在函数内部,不易修改和外泄,相对来说比较安全。

    三、闭包作用

    作用1:隐藏变量,避免全局污染

    作用2:可以读取函数内部的变量

    同时闭包使用不当,优点就变成了缺点:

    缺点1:导致变量不会被垃圾回收机制回收,造成内存消耗

    缺点2:不恰当的使用闭包可能会造成内存泄漏的问题

    这里简单说一下,为什么使用闭包时变量不会被垃圾回收机制收销毁呢,这里需要了解一下JS垃圾回收机制;

    JS规定在一个函数作用域内,程序执行完以后变量就会被销毁,这样可节省内存;

    使用闭包时,按照作用域链的特点,闭包(函数)外面的变量不会被销毁,因为函数会一直被调用,所以一直存在,如果闭包使用过多会造成内存销毁。

    四、闭包应用

    需求:实现变量a 自增

    1、通过全局变量,可以实现,但会污染其他程序

    var a = 10;
    function Add(){
        a++;
        console.log(a);
    }
    Add();
    Add();
    Add();

    2、定义一个局部变量,不污染全局,但是实现不了递增

    var a = 10;
    function Add2(){
        var a = 10;
        a++;
        console.log(a);
    }
    Add2();
    Add2();
    Add2();
    console.log(a);

    3、通过闭包,可以是函数内部局部变量递增,不会影响全部变量,完美!!

    var a  = 10;
    function Add3(){
        var a = 10;
        return function(){
            a++;
            return a;
        };
    };
    var cc =  Add3();
    console.log(cc());
    console.log(cc());
    console.log(cc());
    console.log(a);

    注意:
    
    
    

    
    
    
    转自:JavaScript中闭包的概念、原理、作用及应用 - 知乎 (zhihu.com)
     
    (9条消息) 彻底理解js中的闭包_dovlie的博客-CSDN博客_js闭包
  • 相关阅读:
    word-流程图
    redis介绍
    Linux----硬盘分区
    Vue+restfulframework示例
    Django后端项目---- rest framework(4)
    前端框架VUE----导入Bootstrap以及jQuery的两种方式
    前端框架VUE----补充
    前端框架VUE----表单输入绑定
    前端框架VUE----cli脚手架(框架)
    前端框架VUE----计算属性和侦听器
  • 原文地址:https://www.cnblogs.com/zqlym/p/15117967.html
Copyright © 2020-2023  润新知