这是我参与8月更文挑战的第十三天,活动详情查看:8月更文挑战
执行上下文与作用域
变量或函数的上下文决定了它们可以访问哪些数据,以及它们的行为。每个上下文都有一个关联的变量对象,而这个上下文中定义的所有函数和变量都存在这个对象。
全局上下文是最外层的上下文。在浏览器中,全局上下文就是window对象,因此所有通过var定义的全局变量和函数都会成为window对象的属性和方法。上下文会在其中所有的代码都执行完毕后进行销毁,包括在它上面的所有变量和函数。
每个函数调用都有自己的上下文,当代码执行流进入函数时,函数的上下文被推到一个上下文栈中,在函数执行完毕后,上下文栈会弹出该函数的上下文,将控制权返回给之前的执行上下文。上下文中的代码再执行的时候,会创建变量对象的一个作用域链。这个作用域链决定了各级上下文中的代码在访问变量和函数时候的顺序。
var name = "zijie";
function changeName(){
if (name === "zijie"){
name = "juejin";
}else{
name = "jujinshequ";
}
}
对上面这个例子而言,函数changeName()的作用域链包含两个对象:一个是它自己的变量对象,另一个是全局上下文的变量对象。这个函数内部之所以能够访问变量name,就是因为可以在作用域链中找到它。
作用域链增强
虽然执行上下文主要有全局上下文和函数上下文两种,但是可以通过其他方式来增强作用域链。某些语句会在作用域链前端添加一个上下文,这个上下文在代码执行后会被删除。通常在两张情况下会出现这个现象,即代码块执行到下面任一种情况时:
- try/catch语句的catch块
- with语句