美文网首页
作用域与闭包

作用域与闭包

作者: 卡拉咖啦 | 来源:发表于2019-06-21 00:32 被阅读0次

什么是作用域?作用域(scope)指的是变量存在的范围,这里只讨论 ES 6 之前的全局作用域与函数作用域;

全局变量(global)是在函数外部,比如浏览器的 window,在这个地方声明的变量就是全局变量,全局变量在全局作用域下声明,又可以在函数作用域中使用;

函数作用域(local)是在函数内部,但我们声明了一个函数的时候,就产生了一个 local 作用域,在其中声明的变量,我们就叫局部变量,局部变量不能在外层使用,只能在自己本层作用域,或者下一层作用域中使用。

 // global
function f1() {
  // local_1
  function f2() {
    // local_2
    function f3() {
      // local_3
    }
  }
  function f4() {
    // local_4
  }
}
作用域.png

作用域规则一:正常情况下,外层作用域的变量能在内层中用,但是内层的不能被外层使用。

比如图中的 local_3 中的变量,对于 global, local_1, local_2, local_4 来说都是不存在的。

作用域规则二:变量的作用域取决于它声明时的位置。
举个例子

var a = 1;

function f1(){
  var a = 2;
  f2.call();
}

function f2() {
  console.log(a);
}

f1.call();
// → 1

例子中,我们在全局声明了一个函数 f2, 然后在 f1 中调用它,然而它的作用域依然取决于它最初声明的位置,所以最终打印了 1。

上面的例子是,我们把外面的函数放到了内层的作用域,那么,反过来,我们把内层的的变量、函数拿到外层来,这个变量、函数所在的作用域依然是内部原来的位置。
有没有可能实现呢?有没有必要呢?
实现是没问题的:

var a = 1;
function f1() {
  var a = 2;
  var f2 = function() {
    console.log(a)
  }
  return f2;
}

var f = f1.call(); // f2
f.call() // → 2;

如上,但我们在 f1 中把 f2 return 出来,我们在全局作用域就得到了一个 f2,只不过这个函数的作用域依然是原来的,调用打印 2。

这就是我们常说的闭包(closure),也是我们最常常看到的它的样子。
关于闭包,方老师的文章中有一个简洁朴素的定义:

「函数」和「函数内部能访问到的变量」(也叫环境)的总和,就是一个闭包。

也就是说,闭包就是一个函数(f2)加上它能够用的变量(例子中的 var a = 2),因为作用域的作用规则,我们可以通过函数访问闭包中的变量。

于是,闭包的作用在于,隐藏变量。

关于这个隐藏到底意义多大,我暂时没有太深刻的体会,不过我们可以做个简单的对比。
变量放在全局中,可以被任意操作;
而如果放到闭包中,只能进行我们原型设定好的操作方式。

相关文章

  • 作用域和闭包

    目录 概述 作用域编译过程词法作用域全局作用域函数作用域 闭包循环和闭包闭包的用途性能 总结 概述 作用域和闭包一...

  • 14.JS基础之作用域与闭包

    作用域: 全局作用域 函数作用域 块级作用域(ES6新增) 常见的闭包有:作为函数返回值的闭包与作为函数参数的闭包...

  • 2018-01-07 关于javascript闭包和作用域的理解

    关于 javascript 闭包的一些思考 作用域 词法作用域 函数作用域 块作用域 闭包 什么是作用域? 作用域...

  • js作用域、闭包

    闭包 闭包作用 全局 局部 作用域链

  • javaScript门道之闭包

    闭包的学习路径:变量的作用域 -> 闭包的概念 ->闭包的应用 1.变量的作用域 变量的作用域分为作用于全局和作用...

  • 闭包和高阶函数学习笔记

    一、闭包 闭包的形成与变量的作用域以及变量的生存周期密切相关。 1.1 变量的作用域 变量的作用域:指变量的有效范...

  • 执行环境 & 作用域 & 闭包

    执行环境 & 作用域 & 闭包 执行环境 , 作用域 , 闭包 , 闭包应用 执行环境 执行环境定义了 当前环境的...

  • js 总结七07-19

    作用域 全局 局部 作用域链 闭包

  • 作用域、作用域链、闭包、面向对象、执行上下文

    作用域 作用域链 函数的提前声明 闭包 JavaScript 闭包与类(原型链)之间的开发方式 构造函数和普通函数...

  • 2023-01-12

    变量提升调用栈块级作用域作用域链和闭包 闭包 => 作用域链(词法作用域) => 调用栈(栈溢出) => 上下文...

网友评论

      本文标题:作用域与闭包

      本文链接:https://www.haomeiwen.com/subject/anxeqctx.html