前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >详解javascript作用域和闭包

详解javascript作用域和闭包

作者头像
空空云
发布2018-09-27 11:45:28
6660
发布2018-09-27 11:45:28
举报
文章被收录于专栏:大前端_Web

版权声明:本文为吴孔云博客原创文章,转载请注明出处并带上链接,谢谢。 https://cloud.tencent.com/developer/article/1347516

参考书籍《你不知道的javascript的上卷》

作用域是什么

  • 现代JavaScript已经不再是解释执行的,而是编译执行的。但是与传统的编译语言不同,它不是提前编译,编译结果不能进行移植。编译过程中,同样会经过分词/词法分析,解析/语法分析,代码生成三个阶段
  • 以var a = 2;语句为例,对这一程序语句对处理,需要经过引擎,编译器,作用域三者的配合。其中,引擎从头到尾负责整个javascript程序的编译和执行过程;编译器负责语法分析和代码生成;作用域负责收集并维护由所有声明的标识符组成的系列查询,并实施一套规则,确定当前执行的代码对这些标识符的访问权限
  • 对于var a = 2;编译器首先查找作用域(在函数声明的时候已形成)中是否已经有该名称的变量,然后引擎中执行编译器生成的代码时,会首先查找作用域。如果找到就执行赋值操作,否则就抛出异常
  • 引擎对变量的查找有两种:LHS查询和RHS查询。当变量出现中赋值操作左侧时是LHS查询,出现中右侧是RHS查询

词法作用域

  • 词法作用域就是定义在词法阶段的作用域。词法作用域是由你在写代码时将变量和块作用域写在哪里决定的,词法处理器分析代码时会保持作用域不变
代码语言:javascript
复制
function foo(a){ 
    var b = a * 2; 
    function bar(c){ 
        console.log(a,b,c); 
    } 
    bar(b * 3); 
} 
foo(2); 

这个例子有三级嵌套的作用域

  • 作用域查找会在找到第一个匹配的标识符时停止
  • eval和with可以欺骗词法作用域,不推荐使用

函数作用域和块作用域

  • JavaScript具有基于函数的作用域,属于这个函数的变量都可以在整个函数的范围内使用及复用 (function fun(){})()
  • 函数表达式和函数声明的区别是看function关键字出现在声明中的位置。如果function是声明中的第一个词,那么就是一个函数声明,否则就是一个函数表达式
  • with,try/catch具有块作用域,方便好用的实现块级作用域的是es6带来的let关键字

作用域闭包

  • 内部函数传递到所在词法作用域以外,它都会持有对原始定义作用域的引用,无论中何处执行这个函数都会使用闭包
  • 本质上,无论何时何地,如果将函数当作第一级的值类型并到处传递,就会看到闭包在这些函数中的应用。在定时器,事件监听器,ajax请求,web workers或者其他任何异步任务中,只要使用了回调函数,实际上就是在使用闭包(闭包是函数的嵌套定义,及该函数定义时候的作用域链)
  • 模块的封装利用了闭包,将内部变量隐藏,并返还一个公共api的对象,这一返回的对象对模块的私有变量形成闭包访问。

动态作用域

  • 词法作用域是一套引擎如何寻找变量以及会在何处找到变量的规则。词法作用域最重要的特征是它的定义过程发生中代码的书写阶段
  • 动态作用域让作用域作为一个在运行时就被动态确定的形式,而不是在写代码时进行静态确定的形式。
代码语言:javascript
复制
function foo(){ 
    console.log(a);//2 
} 
function bar(){ 
    var a = 3; 
    foo(); 
} 
var a = 2; 
bar();

总结

JavaScript不具备动态作用域。 但是this机制中某种程度上很像动态作用域,this关注函数如何调用

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2016年12月14日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 作用域是什么
  • 词法作用域
  • 函数作用域和块作用域
  • 作用域闭包
  • 动态作用域
  • 总结
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档