zoukankan      html  css  js  c++  java
  • javascript中闭包的概念

    这个是每个前端工程师绕不开的一个问题,网上各种资料很多,整个春节,我仔细研读了红皮经典中关于这一块的注释,加深了对这一块的理解。

    有好几个概念需要重申一下。以下都是我的理解:

    1. 闭包是javascript中的一种程序结构,可以访问函数内部所有的变量。

    2. 闭包的作用,以一个函数为例:

    function a(){
        var i = 0;
        function b(){
            alert(++i);
        }
        return b; 
    }
    
    var c = a();

    闭包的作用:a执行完并返回后,闭包将使得Javascript的垃圾回收机制不会收回a所占用的资源,因为a的内部函数b的执行需要依赖a中的变量。

    如果a返回的不是一个函数而是其他的某一个值,情况就不一样了。a执行完后,b并不会被外部引用,会一起被GC回收。

    3. 闭包的内部细微情况:

      这里涉及到了好几个概念,我根据自己的理解记一下。

      函数在每次执行的时候,会创建一个执行环境,在这个环境中,函数会将自己的作用域链存在函数的scope属性中。

      然后,函数会用this arguments 参数来初始化自身的活动对象。scope[0]=>函数内部的活动对象,scope[1]=>函数外部的活动对象,scope[2]=>外部的外部活动对象....一直到作用域链的终点:全局执行环境。

      正是因为闭包中保存的是活动对象---整个变量对象,而不是某个特殊的变量,因此,闭包只能保存函数中任何变量的最后一个值。

      又到了展示经典代码的时刻

    function test(){
        var result = [];
        for(var i=0; i<10; i++){
            result[i] = function(){
                return i;
            }
        }
        return result;       
    }
    
    var arr = test();
    for(var i=0; i<arr.length; i++){
        console.log(arr[i]());
    }

    类似的例子很多,比如onclick例子,等等,这里是从经典红书中借鉴的例子。

    在网上看到了一个非常好的 介绍这块的 英文的PPT,好像是微软内部的。介绍的比较全面,也没有那么晦涩,先给个地址。

    https://app.box.com/shared/elkumrpfng

    说下从这里面看到的一些,补充上面的内容。

    闭包是个函数,而它「记住了周围发生了什么」。表现为由「一个函数」体中定义了「另个函数」

    function outer () {
        ...
        function inner () {
            ...
        }
    }

    另外,著名博主阮一峰的一篇文章,也很浅显易懂。但我觉得,内容好像少了一点。
    摘要一点: 由于在Javascript语言中,只有函数内部的子函数才能读取局部变量,因此可以把闭包简单理解成"定义在一个函数内部的函数"。所以,在本质上,闭包就是将函数内部和函数外部连接起来的一座桥梁。

    闭包可以用在许多地方。它的最大用处有两个,一个是前面提到的可以读取函数内部的变量,另一个就是让这些变量的值始终保持在内存中。

        function f1(){
       var n=999;
       nAdd=function(){n+=1}
       function f2(){
         alert(n);
       }
        return f2;
       }
      var result=f1();
      result(); // 999
      nAdd();
      result(); // 1000

    他的这个例子有点奇怪哈,其实这个例子的重点是想说:

    f1是f2的父函数,f1执行后,f2被赋给了一个全局变量,这导致f2始终在内存中,而f2的存在依赖于f1,因此f1也始终在内存中,因此,f1中的变量不会在调用结束后,被垃圾回收机制(garbage collection)回收。

  • 相关阅读:
    java面试之String源码中equals具体实现
    JVM虚拟机—JVM的垃圾回收机制(转载)
    Mysql学习笔记—视图
    Mysql学习笔记—索引
    JVM虚拟机—JVM内存
    设计模式—装饰器模式
    设计模式—代理模式
    设计模式—适配器模式
    设计模式—观察者模式
    设计模式—建造者模式
  • 原文地址:https://www.cnblogs.com/lxin/p/3546738.html
Copyright © 2011-2022 走看看