通过函数作用域和块级作用域看javascript的作用域链


Posted in Javascript onAugust 05, 2018

在ES6之前,javascript只有全局作用域和函数作用域。所谓作用域就是一个变量定义并能够被访问到的范围。也就是说如果一个变量定义在全局(window)上,那么在任何地方都能访问到这个变量,如果这个变量定义在函数内部,那么就只能在函数内部访问到这个变量。

全局作用域只要页面没关闭就会一直存在,而函数作用域只有在函数执行的时候才存在,执行完就销毁。且每次执行函数都会创建一个新的作用域。

那么什么是作用域链呢?
在了解作用域链之前,我们先了解一个执行期上下文的概念。

执行期上下文:当函数执行时,会创建一个称为执行期上下文的内部对象(即AO或GO),一个执行期上下文定义了一个函数的执行环境,函数每次执行时对应的执行期上下文都是独一无二的,所以每次调用一个函数都会创建一个新的执行期上下文,当函数执行完毕,所产生的执行期上下文被销毁。

作用域链就是函数中[[scope]]属性所存储的执行期上下文对象的集合,这个集合呈链式链接,我们把这种链式链接叫做作用域链。

作用域链更像是一种包含的关系。比如说函数A内部定义了一个函数B,所以B的定义是依赖于A的,也就是说B在A的内部,那么B中就可以访问A的中的变量和方法。这种一层一层向上依赖的关系就构成了作用域链。

为了更好理解,我们直接看例子。

var name = 'xiaoyu';
function fn1() {};
function fn2() {
 var num = 10;
 function fn3() {
  var num1 = 10;
  console.log(num);
 };
 return fn3;
}
var fn4 = fn2();

通过函数作用域和块级作用域看javascript的作用域链

在上个例子我们知道,fn2执行的时候返回fn3,产生了闭包。但是一个函数执行然后返回另一个函数都会产生闭包嘛?我们来看一下。

var name = 'xiaoyu';
function fn1() {};
function fn2() {
 var num = 10;
 function fn3() {//fn3函数没有依赖fn2函数内的变量
  var num1 = 10;
  console.log(num1);
 };
 return fn3;
}
var fn4 = fn2();

通过函数作用域和块级作用域看javascript的作用域链

了解了作用域链之后,我们来看一个小例子,巩固一下。

var age = 10;
var obj = {
 age: 12,
 test: function() {
  console.log(age);
  console.log(obj.age);
  console.log(this.age);
 }
}
obj.test();

console.log(this.age)打印出12不难理解,但是为什么console.log(age)不也应该打印出12嘛。

我们说test执行时首先会在自己的作用域内查看有没有age变量,然后再沿着作用域链往上到全局作用域查找age变量,全局作用域下有age变量和data变量。所以console.log(age)打印出的10,如果要打印出12则需要访问obj.age。

ES6的块级作用域

在ES6之后,通过let和const引入了块级作用域。即通过let和const声明的变量只在声明所在的块级作用域内有效,并且let声明的变量虽然属于全局变量,但不再属于全局对象window。

我们通过一段代码来看一下引入块级作用域后,函数的作用域链的变化。

var age = 10;
let obj = {
 age: 12,
 test: function() {
   console.log(age);
   console.log(obj.age);
   console.log(this.age);
 }
}
obj.test();

通过函数作用域和块级作用域看javascript的作用域链

Javascript 相关文章推荐
基于jquery的让页面控件不可用的实现代码
Apr 27 Javascript
学习面向对象之面向对象的基本概念:对象和其他基本要素
Nov 30 Javascript
关于jQuery参考实例 1.0 jQuery的哲学
Apr 07 Javascript
jquery 获取dom固定元素 添加样式的简单实例
Feb 04 Javascript
根据当前时间在jsp页面上显示上午或下午
Aug 18 Javascript
jQuery中offsetParent()方法用法实例
Jan 19 Javascript
jquery判断checkbox是否选中及改变checkbox状态的实现方法
May 26 Javascript
微信小程序 自定义对话框实例详解
Jan 20 Javascript
jQuery插件zTree实现清空选中第一个节点所有子节点的方法
Mar 08 Javascript
Angular2 父子组件通信方式的示例
Jan 29 Javascript
基于原生js实现判断元素是否有指定class名
Jul 11 Javascript
解决Vue中的生命周期beforeDestory不触发的问题
Jul 21 Javascript
vue实现简单的MVVM框架
Aug 05 #Javascript
使用D3.js+Vue实现一个简单的柱形图
Aug 05 #Javascript
详解Require.js与Sea.js的区别
Aug 05 #Javascript
vue中关闭eslint的方法分析
Aug 04 #Javascript
详解Vue取消eslint语法限制
Aug 04 #Javascript
JavaScript原型对象、构造函数和实例对象功能与用法详解
Aug 04 #Javascript
JavaScript中变量、指针和引用功能与操作示例
Aug 04 #Javascript
You might like
如何把PHP转成EXE文件
2006/10/09 PHP
ThinkPHP中pathinfo的访问模式、路径访问模式及URL重写总结
2014/08/23 PHP
php array_walk 对数组中的每个元素应用用户自定义函数详解
2016/11/18 PHP
php图像处理函数imagecopyresampled用法详解
2016/12/02 PHP
PHP自定义递归函数实现数组转JSON功能【支持GBK编码】
2018/07/17 PHP
ThinkPHP类似AOP思想的参数验证的实现方法
2019/12/18 PHP
PHP 扩展Memcached命令用法实例总结
2020/06/04 PHP
学习YUI.Ext 第七天--关于View&JSONView
2007/03/10 Javascript
jQuery 打造动态下滑菜单实现说明
2010/04/15 Javascript
google 搜索框添加关键字实现代码
2010/04/24 Javascript
JavaScript中几个重要的属性(this、constructor、prototype)介绍
2013/05/19 Javascript
Chrome下ifame父窗口调用子窗口的问题示例探讨
2014/03/17 Javascript
json中换行符的处理方法示例介绍
2014/06/10 Javascript
吐槽一下我所了解的Node.js
2014/10/08 Javascript
JS+CSS实现的拖动分页效果实例
2015/05/11 Javascript
JavaScript中exec函数用法实例分析
2015/06/08 Javascript
jQuery on()方法绑定动态元素的点击事件实例代码浅析
2016/06/16 Javascript
基于MVC5和Bootstrap的jQuery TreeView树形控件(二)之数据支持json字符串、list集合
2016/08/11 Javascript
angularjs 表单密码验证自定义指令实现代码
2016/10/27 Javascript
Bootstrap表格使用方法详解
2017/02/17 Javascript
JS排序之选择排序详解
2017/04/08 Javascript
angularjs指令之绑定策略(@、=、&)
2017/04/13 Javascript
Vue.js常用指令的使用小结
2017/06/23 Javascript
JavaScript程序设计高级算法之动态规划实例分析
2017/11/24 Javascript
JS实现验证码倒计时的注册页面
2018/01/02 Javascript
vue-cli项目中使用公用的提示弹层tips或加载loading组件实例详解
2018/05/28 Javascript
[55:32]2018DOTA2亚洲邀请赛 4.4 淘汰赛 EG vs LGD 第二场
2018/04/05 DOTA
Python爬虫:将headers请求头字符串转为字典的方法
2019/08/21 Python
给大家整理了19个pythonic的编程习惯(小结)
2019/09/25 Python
Python使用Chrome插件实现爬虫过程图解
2020/06/09 Python
利用纯CSS3实现文字向右循环闪过效果实例(可用于移动端)
2017/06/15 HTML / CSS
html5给汉字加拼音加进度条的实现代码
2020/04/07 HTML / CSS
美国派对用品及装饰品网上商店:Shindigz
2016/07/30 全球购物
教师演讲稿大全
2014/05/16 职场文书
无毒社区工作方案
2014/05/23 职场文书
仓库管理制度范本
2015/08/04 职场文书