谈一谈js中的执行环境及作用域


Posted in Javascript onMarch 30, 2016

最近在面试时被问到了对作用域链的理解,感觉当时回答的不是很好,今天就来说说js中的作用域链吧。

首先来说说js中的执行环境,所谓执行环境(有时也称环境)它是JavaScript中最为重要的一个概念。执行环境定义了变量或函数有权访问的其他数据 ,决定了它们各自的行为。而每个执行环境都有一个与之相关的变量对象,环境中定义的所有变量和函数都保存在这个对象中。

理解了执行环境,现在就看看什么是作用域链吧。每个函数都有自己的执行环境,当代码在执行环境中执行时,就会创建变量对象的作用域链。作用域链保证了对执行环境有权访问所有变量和函数的有序访问。作用域链的前端,始终都是当前执行的代码所在的环境的变量对象,如果环境是一个函数,那么它的变量对象就是该函数的活动对象。作用域链的下一个变量对象来自包含(外部)环境,再下一个变量对象来自下一个包含环境。这样一直延续到全局执行环境,记住,全局执行环境的变量对象永远是作用域中的最后一个对象。

请看下面的例子:

var scope="global";
function foo(){
  console.log(scope);
}  
foo();

在这个例子中,函数foo()的作用域链包含了两个对象,一个是它自身对象,另一个是全局环境中的变量对象。因为我们可以在这个作用域链中找的scope,所以可以在函数内部里访问到它。

在看一个例子:

var color = "blue";
function changeColor(){
  var anoterColor = "red";
  function swapColor(){
    var tempColor = anoterColor;
    anoterColor = color;
    color = tempColor;
    console.log(color);
  }
  swapColor();
}
changeColor();

在这个例子中,有三个执行环境:全局环境、changeColor()的局部环境和swapColor()局部环境。我们来看看这个例子的作用域链是怎样的吧。

谈一谈js中的执行环境及作用域

图中的矩形表示特定的执行环境。我们可以看到变量tempColor只能在swapColor()环境中访问到,而在changeColor()的局部环境还是全局环境中都无法访问到它。因此我们可以得到一个结论:内部的环境可以通过作用域链访问所有的外部环境,但外部的环境无法访问内部的环境中的任何变量和函数。每个环境都可以向上搜索作用域链,以查询变量和函数名;但是任何环境都不能通过向下搜索作用域而进入另一个执行环境。

作用域中我还想说说的是:js没有块级作用域

为什么说js没有块级作用域呢?我们来看下面的代码:

if(true){
 var color = "blue"; 
}
alert(color);  //"blue"

咦,为什么color在if语句执行完毕后被销毁呢?哈哈,如果在C、C++或Java中,color确实会被销毁,但在JavaScript中,if语句中的变量声明会将变量添加到当前的执行环境中(在这里是全局环境)中。特别地,在for语句时要牢记这一差异,例如:

for(var i = 0;i< 10; i++){
doSomething(i);
}
alert(i);    //10

记住:在JavaScript中,由for语句创建的变量i即使在for循环执行结束之后,也依然会存在于循环外部的执行环境中。

以上就是本文的全部内容,希望对大家的学习有所帮助。

Javascript 相关文章推荐
syntaxhighlighter 使用方法
Jul 02 Javascript
javascript 面向对象编程 function也是类
Sep 17 Javascript
利用JS解决ie6不支持max-width,max-height问题的方法
Jan 02 Javascript
jquery的ajax和getJson跨域获取json数据的实现方法
Feb 04 Javascript
jquery实现的Accordion折叠面板效果代码
Sep 02 Javascript
Jquery Easyui自定义下拉框组件使用详解(21)
Dec 31 Javascript
微信小程序 Template详解及简单实例
Jan 05 Javascript
Bootstrap中data-target 到底是什么
Feb 14 Javascript
js时间查询插件使用详解
Apr 07 Javascript
深入koa-bodyparser原理解析
Jan 16 Javascript
利用js实现简易红绿灯
Oct 15 Javascript
8个JS的reduce使用实例和reduce操作方式
Oct 05 Javascript
js实现(全选)多选按钮的方法【附实例】
Mar 30 #Javascript
用JS生成UUID的方法实例
Mar 30 #Javascript
如何通过js实现图片预览功能【附实例代码】
Mar 30 #Javascript
jquery $.trim()去除字符串空格的实现方法【附图例】
Mar 30 #Javascript
jquery实现简单的banner轮播效果【实例】
Mar 30 #Javascript
jquery实现一个简单的表单验证实例
Mar 30 #Javascript
js实现密码强度检测【附示例】
Mar 30 #Javascript
You might like
用php将任何格式视频转为flv的代码
2009/09/03 PHP
解析PHP提交后跳转
2013/06/23 PHP
php 根据url自动生成缩略图并处理高并发问题
2014/01/23 PHP
Thinkphp5 自定义上传文件名的实现方法
2019/07/23 PHP
javascript实现的距离现在多长时间后的一个格式化的日期
2009/10/29 Javascript
JavaScript中判断函数是new还是()调用的区别说明
2011/04/07 Javascript
js实现获取焦点后光标在字符串后
2014/09/17 Javascript
实例详解JavaScript获取链接参数的方法
2016/01/01 Javascript
超链接怎么正确调用javascript函数
2016/05/23 Javascript
javascript垃圾收集机制的原理分析
2016/12/08 Javascript
Vue中添加过渡效果的方法
2017/03/16 Javascript
JavaScript该如何学习 怎样轻松学习JavaScript
2017/06/12 Javascript
微信小程序 五星评分的实现实例
2017/08/04 Javascript
微信小程序使用swiper组件实现层叠轮播图
2018/11/04 Javascript
Vue项目中如何使用Axios封装http请求详解
2019/10/23 Javascript
Vuejs中的watch实例详解(监听者)
2020/01/05 Javascript
[42:20]Winstrike vs VGJ.S 2018国际邀请赛淘汰赛BO3 第二场 8.23
2018/08/24 DOTA
解决pycharm py文件运行后停止按钮变成了灰色的问题
2018/11/29 Python
使用PyQtGraph绘制精美的股票行情K线图的示例代码
2019/03/14 Python
Pyqt5 基本界面组件之inputDialog的使用
2019/06/25 Python
pytorch方法测试详解——归一化(BatchNorm2d)
2020/01/15 Python
Python作用域与名字空间原理详解
2020/03/21 Python
CSS3 不定高宽垂直水平居中的几种方式
2020/03/26 HTML / CSS
html5 Canvas画图教程(7)—canvas里画曲线之quadraticCurveTo方法
2013/01/09 HTML / CSS
极简的HTML5模版
2015/07/09 HTML / CSS
草莓网化妆品澳大利亚站:Strawberrynet AU
2017/12/18 全球购物
端口镜像是怎么实现的
2014/03/25 面试题
车队司机自我鉴定
2014/03/02 职场文书
企业宣传工作方案
2014/06/02 职场文书
常务副县长“三严三实”对照检查材料思想汇报
2014/10/05 职场文书
教师先进事迹材料
2014/12/16 职场文书
幼儿园教师个人总结
2015/02/05 职场文书
教育教学工作反思
2016/02/24 职场文书
复制别人的成功真的会成功吗?
2019/10/17 职场文书
Python数据分析入门之教你怎么搭建环境
2021/05/13 Python
SpringCloud超详细讲解Feign声明式服务调用
2022/06/21 Java/Android