js 函数的执行环境和作用域链的深入解析


Posted in Javascript onNovember 01, 2009

第一步. 定义后:每个已定义函数,都有一个内在属性[scope],其对应一个对象的列表,列表中的对象仅能内部访问。

例如:建立一个全局函数A,那么A的[Scope]内部属性中只包含一个全局对象(Global Object),而如果我们在A中创建一个新的函数B,那么B的[Scope]属性中就包含两个对象,函数A的Activation Object对象在前面,全局对象(Global Object)排在后面。

简而言之,一个函数的[Scope]属性中对象列表的顺序是上一层函数的Activation Object对象,然后是上上层的,一直到最外层的全局对象。

第二步.执行时:当一个函数被执行的时候,会自动创建一个可以执行的对象(Execution Object),并同时绑定一个作用域链(Scope Chain)。作用域链会通过下面两个步骤来建立,用于进行标识符解析。

首先,将函数对象[Scope]内部属性中的对象,按顺序复制到作用域链Scope Chain中。
其次,在函数执行时,会创建一个新的Activation Object对象,这个对象中包含了this、参数(arguments)、局部变量(包括命名的参数)的定义,这个Activation Object对象会被置于作用域链的最前面。
所以在Scope Chain中最后顺序是本函数的Activation Object,然后是上层函数的Activation Object,再上上层的Activation Object,一直到Global Object。

当执行js代码的过程中,遇到一个标识符,就会根据标识符的名称,在执行上下文(Execution Context)的作用域链中进行搜索。从作用域链的第一个对象(该函数的Activation Object对象)开始,如果没有找到,就搜索作用域链中的下一个对象,如此往复,直到找到了标识符的定义。如果在搜索完作用域中的最后一个对象,也就是全局对象(Global Object)以后也没有找到,则会抛出一个错误,提示undefined。

由此而来的建议:

1. 尽量使用局部变量,这不仅仅是涉及到私有属性的问题,局部的变量从以上过程中可以看到,能够减少搜索的时间(注:在一般的情况下,不包括浏览器的优化行为)。

2. 避免使用with语句。因为它会修改执行上下文(Execution Context)的作用域链,在最前面添加一个对象(Variable Object)。同理,对于try-catch语句中的catch语句块也类似。

Javascript 相关文章推荐
XML的代替者----JSON
Jul 21 Javascript
Javascript 阻止javascript事件冒泡,获取控件ID值
Jun 27 Javascript
js/jquery解析json和数组格式的方法详解
Jan 09 Javascript
JS+CSS实现弹出全屏灰黑色透明遮罩效果的方法
Dec 20 Javascript
js实现拖拽效果
Feb 12 Javascript
AngularJS  双向数据绑定详解简单实例
Oct 20 Javascript
Javascript vue.js表格分页,ajax异步加载数据
Oct 24 Javascript
微信小程序开发探究
Dec 27 Javascript
jQuery插件版本冲突的处理方法分析
Jan 16 Javascript
详解使用Visual Studio Code对Node.js进行断点调试
Sep 14 Javascript
vue vuex vue-rouert后台项目——权限路由(适合初学)
Dec 29 Javascript
Node.js + express基本用法教程
Mar 14 Javascript
提高网站性能之 如何对待JavaScript
Oct 31 #Javascript
JavaScript Sort 表格排序
Oct 31 #Javascript
DOM 脚本编程中的兄弟节点
Oct 31 #Javascript
javascript GUID生成器实现代码
Oct 31 #Javascript
json 实例详细说明教程
Oct 31 #Javascript
json 入门基础教程 推荐
Oct 31 #Javascript
jquery text()要注意啦
Oct 30 #Javascript
You might like
超神学院:鹤熙已踏入神圣领域,实力不比凯莎弱
2020/03/02 国漫
PHP 文章中的远程图片采集到本地的代码
2009/07/30 PHP
快速解决jQuery与其他库冲突的方法介绍
2014/01/02 Javascript
基于JavaScript怎么实现让歌词滚动播放
2015/11/03 Javascript
AngularJS使用ng-options指令实现下拉框
2016/08/23 Javascript
jQuery中JSONP的两种实现方式详解
2016/09/26 Javascript
Javascript中document.referrer隐藏来源的方法
2017/01/16 Javascript
JavaScript实现简单的四则运算计算器完整实例
2017/04/28 Javascript
基于jQuery封装的分页组件
2017/06/26 jQuery
vue 2.0封装model组件的方法
2017/08/03 Javascript
基于canvas粒子系统的构建详解
2017/08/31 Javascript
AngularJS实现动态切换样式的方法分析
2018/06/26 Javascript
微信小程序静默登录的实现代码
2020/01/08 Javascript
Vue实现图书管理小案例
2020/12/03 Vue.js
Python升级提示Tkinter模块找不到的解决方法
2014/08/22 Python
Python实现读取并保存文件的类
2017/05/11 Python
Python学习入门之区块链详解
2017/07/25 Python
Python实现文件信息进行合并实例代码
2018/01/17 Python
Python列表生成式与生成器操作示例
2018/08/01 Python
python实现电子产品商店
2019/02/26 Python
Django上线部署之IIS的配置方法
2019/08/22 Python
python实现飞机大战项目
2020/03/11 Python
在python3.9下如何安装scrapy的方法
2021/02/03 Python
SQL中where和having的区别
2012/06/17 面试题
关于.NET, HTML的五个问题
2012/08/29 面试题
初一地理教学反思
2014/01/16 职场文书
学生思想表现的评语
2014/01/30 职场文书
总结表彰大会主持词
2014/03/26 职场文书
525心理活动总结
2014/07/04 职场文书
五一劳动节演讲稿
2014/09/12 职场文书
白鹤梁导游词
2015/02/06 职场文书
2015社区精神文明建设工作总结
2015/04/21 职场文书
大学开学典礼新闻稿
2015/07/17 职场文书
找规律教学反思
2016/02/23 职场文书
小学四年级作文之人物作文
2019/11/06 职场文书
Node.js实现爬取网站图片的示例代码
2022/04/04 NodeJs