零碎知识点摘要-0819-闭包

196 阅读2分钟
概念

闭包是“函数”和声明该函数的“词法环境”的组合。 个人理解,通俗点就是,这个函数和他里面的变量的值,整个包裹起来,这个东西才叫做闭包。

闭包一般会是在函数内部的,就是一个“大函数”里面的另一个“小函数”,这个“小函数”能访问到“大函数”里面声明的变量,而且能保存起来。 举两个例子,比较一下

function init() {
    var name = "Mozilla"; // name 是一个被 init 创建的局部变量
    function displayName() { // displayName() 是内部函数,一个闭包
        alert(name); // 使用了父函数中声明的变量
    }
    displayName();
}
init();
function makeFunc() {
    var name = "Mozilla";
    function displayName() {
        alert(name);
    }
    return displayName;
}

var myFunc = makeFunc();
myFunc();

两个代码效果是一样的,但是有一点不同,一个是在 makeFunc 函数内部执行,另外一个是在 makeFunc 外部执行。

其中原理

在 Javascript 中,这样的函数会形成闭包,在上述的概念里,闭包内部创建了这个函数的词法环境,包含了这个闭包创建时所能访问的所有局部变量,所以,虽然外部函数 makeFunc 运行完了,但是创建了一个闭包。并且,有一点很重要,你生成一个闭包,他的内部环境,就生成了,再去生成一个相同的闭包,他的内部环境是独立的。

用法
  1. 利用闭包,封装又独特环境变量的函数,去结合用户的点击事件使用。 例子:developer.mozilla.org/zh-CN/docs/…

  2. 用闭包模拟私有方法。私有方法不仅仅有利于限制对代码的访问;还提供了管理全局命名空间的强大能力,避免非核心的方法弄乱了代码的公共接口部分。 例子

var Counter = (function() {
  var privateCounter = 0;
  function changeBy(val) {
    privateCounter += val;
  }
  return {
    increment: function() {
      changeBy(1);
    },
    decrement: function() {
      changeBy(-1);
    },
    value: function() {
      return privateCounter;
    }
  }   
})();

console.log(Counter.value()); /* logs 0 */
Counter.increment();
Counter.increment();
console.log(Counter.value()); /* logs 2 */
Counter.decrement();
console.log(Counter.value()); /* logs 1 */

另一种变化

var makeCounter = function() {
  var privateCounter = 0;
  function changeBy(val) {
    privateCounter += val;
  }
  return {
    increment: function() {
      changeBy(1);
    },
    decrement: function() {
      changeBy(-1);
    },
    value: function() {
      return privateCounter;
    }
  }  
};

var Counter1 = makeCounter();
var Counter2 = makeCounter();
console.log(Counter1.value()); /* logs 0 */
Counter1.increment();
Counter1.increment();
console.log(Counter1.value()); /* logs 2 */
Counter1.decrement();
console.log(Counter1.value()); /* logs 1 */
console.log(Counter2.value()); /* logs 0 */
闭包性能

如果不是某些特定任务需要使用闭包,在其他函数中创建闭包是不明智的,因为闭包在处理速度和内存消耗方面对脚本性能有负面影响。


以上内容均自己借鉴写的摘要,不做任何商业用途,若侵权则删除。