闭包

  • 回调函数:回调函数就是一个参数,将这个函数作为参数传到另一个函数里面,当那个函数执行完之后,再执行传进去的这个函数,这个过程就叫做回调。回调,就是回头调用的意思。主函数的事先干完,回头再调用传进来的那个函数。(参考https://www.cnblogs.com/lishuxue/p/5999682.html)
//定义主函数,回调函数作为参数
function A(callback) {
    callback();  
    console.log('我是主函数');      
}

//定义回调函数
function B(){
    setTimeout("console.log('我是回调函数')", 3000);//模仿耗时操作  
}

//调用主函数,将函数B传进去
A(B);

//输出结果
我是主函数
我是回调函数


/*上面的代码中,我们先定义了主函数和回调函数,然后再去调用主函数,将回调函数传进去。
定义主函数的时候,我们让代码先去执行callback()回调函数,但输出结果却是后输出回调函数的内容。
这就说明了主函数不用等待回调函数执行完,可以接着执行自己的代码。
所以一般回调函数都用在耗时操作上面。比如ajax请求,比如处理文件等。*/

闭包

  • 嵌套的函数可以访问在其外部声明的变量
  • 闭包的函数实例,它们共享相同的函数定义,但是保存了不同的词法环境(变量的域)

实用的闭包:

  • 在 Web 中大部分我们所写的 JavaScript 代码都是基于事件的 — 定义某种行为,然后将其添加到用户触发的事件之上(比如点击或者按键)。我们的代码通常作为回调:为响应事件而执行的函数
function makeSizer(size) {
  return function() {
    document.body.style.fontSize = size + 'px';
  };
}

var size12 = makeSizer(12);
var size14 = makeSizer(14);
var size16 = makeSizer(16);

//分别添加到按钮的点击事件上
document.getElementById('size-12').onclick = size12;
document.getElementById('size-14').onclick = size14;
document.getElementById('size-16').onclick = size16;

12
14
16

用闭包模拟私有方法

  • 使用闭包来定义公共函数,并令其可以访问私有函数和变量
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 */
/*外部能通过这几个接口调用changby 
只创建了一个词法环境,为三个函数所共享:
Counter.increment,Counter.decrement 和 Counter.value*/
  • 在一个闭包内对变量的修改,不会影响到另外一个闭包中的变量
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 */
/*请注意两个计数器 counter1 和 counter2 是如何维护它们各自的独立性的。
每个闭包都是引用自己词法作用域内的变量 privateCounter 。
每次调用其中一个计数器时,通过改变这个变量的值,会改变这个闭包的词法环境。
然而在一个闭包内对变量的修改,不会影响到另外一个闭包中的变量*/

参考:http://book.jirengu.com/fe/%E5%89%8D%E7%AB%AF%E5%9F%BA%E7%A1%80/Javascript/%E9%97%AD%E5%8C%85.html

你可能感兴趣的:(闭包)