龙空技术网

带你走进JavaScript世界系列——作用域(链)

资深北漂假码农 125

前言:

目前同学们对“js的块级作用域”大概比较讲究,同学们都需要分析一些“js的块级作用域”的相关资讯。那么小编也在网络上汇集了一些关于“js的块级作用域””的相关内容,希望各位老铁们能喜欢,我们一起来学习一下吧!

在前面的文章中,我们已经介绍过了JavaScript的执行环境,主要有全局执行环境和局部(函数)执行环境。

延长作用域链

虽然执行环境的类型总共有两种,但是还是有办法来延长作用域链。因为有些语句可以在作用域链的前端临时增加一个变量对象,该变量对象会在代码执行后被移除。当执行流程进入下列任何一个语句时,作用域链就会得到加长:

try-catch语句的catch块;

with语句。

这两个语句都会在作用域链的前端添加一个变量对象。对with语句来说,会将指定的对象添加到作用域链中。对catch语句来说,会创建一个新的变量对象,其中包含的是被抛出的错误对象的声明。请看下面的例子:

with语句延长作用域链

没有块级作用域

JavaScript中没有块级作用域,请看一下面的例子:

一个简单的没有块级作用域

在上面的if语句里面定义了变量 name。如果是Java中或其他有块级作用域的语言中,name会在if语句执行完被销毁。但是在JavaScript中,if语句中的变量会被添加到当前的执行环境中(上面的例子是全局环境)。特别是在使用for循环结构时,一定要记得这点差异:

for循环中的差异

声明变量

在JavaScript中,使用var关键字声明的变量会被自动加入到最接近的环境中。在函数内部,最接近的环境就是函数的局部环境;在with语句中,最接近的环境是函数的环境。如果初始化变量时没有使用var,该变量会被自动添加到全局环境中。请看下面的例子:

使用var关键字声明的变量

上面的例子中可以看出,使用了var关键字声明的变量,会被加入到最接近的环境中,在外部环境中将无法访问该变量,但是如果改成下面这样的,结果又不一样了:

未使用var声明的变量会被添加到全局环境中

查询标识符

当在某个环境中读取或写入而引用一个标识符时,必须通过搜索来确定该标识符实际代表什么。搜索的过程是从作用域链的前端开始,向上逐级查询与给定名字匹配的标识符。如果在局部环境中找到了该标识符,搜索结束。如果在局部环境中没有找到该变量名,则继续沿作用域链向上搜索,搜索过程将一直追溯到全局环境。如果在全局环境中也没有找到这个标识符,则表示该变量未声明。请看下面的示例:

标识符搜索过程

但是如果存在一个局部变量的定义,则搜索会自动停止,不再进入下一个变量对象:

存在局部变量的搜索过程

标签: #js的块级作用域 #jswith作用域 #javascript作用链域