浅谈javascript作用域
栏目: JavaScript · 发布时间: 5年前
内容简介:作用域负责收集并维护由所有声明的变量组成的集合,等待引擎的查找。可以看出'L'和'R'分别代表左侧和右侧,即赋值的左侧和右侧。赋值不只是查询失败会出现什么情况
理解作用域
作用域负责收集并维护由所有声明的变量组成的集合,等待引擎的查找。
var a = 2; console.log(a); // 2 console.log(b); // ReferenceError: b is not defined
-
var a = 2
可以分解为var a;
a = 2
。当遇到var a
时,编译器会询问作用域是否存在变量a
。如果存在,则忽略该声明,否则会在当前作用域的集合中声明一个新的变量a
。 -
遇到
a = 2
时,引擎会询问当前作用域是否存在变量,如果未找到,则会继续在上级作用域查找。如果最终找到就会将2赋值给变量a
。 -
console.log(a)
时,引擎会去作用域中查找a
,找到把结果返回,输出2,console.log(b)
时,引擎未在作用域查找到b
,抛出异常。
LHS和RHS查询
可以看出'L'和'R'分别代表左侧和右侧,即赋值的左侧和右侧。赋值不只是 =
的赋值,函数参数的传递也是一种赋值操作。
var a = 2; // LHS查询,a出现在赋值左侧 console.log(a); // RHS查询, a出现在赋值右侧,将变量a赋值给参数
查询失败会出现什么情况
对于LHS查询 a = 2
若a未找到,在非严格模式下并不会报错,而变量 a 会被自动创建。而对于 RHS 来说,直接使用未声明的变量就会报 ReferenceError。
console.log(b); // ReferenceError: b is not defined
词法作用域
作用域主要有两种工作模型:词法作用域和动态作用域。
词法作用域就是定义在词法阶段的作用域。换句话说,词法作用域是由你写代码时变量和块作用域写在哪决定的。
function foo(a) { var b = a * 2; function bar(a) { console.log(a, b, c); } bar(b*3); } foo(2);
在这个例子有三个逐级嵌套的作用域。
- 全局作用域,包含一个标识符:foo
- foo所创建的作用域,包含三个标识符:a, bar, b
- bar所创建的作用域,包含一个标识符:c
函数作用域
函数作用域是指属于这个函数的变量都可以在整个函数范围内使用和复用。
function fn() { var a = 2; console.log(a); // 2 } console.log(a); // ReferenceError: a is not defined
从中可以看出,函数外部将无法访问函数内部的变量。
块作用域
ES6引入 let
、 const
将变量绑定到所在块作用域(通常是{...}内部)
{ let a = 2; console.log(a); // 2 } console.log(a); // ReferenceError: a is not defined
除 let
、 const
外, with
、 try/catch
的 catch
分句会创建一个块作用域。
小结
函数是Javascript中最常见的作用域单元。但函数不是唯一的作用域单元。块作用域属于某个代码块(通常指{...}内部)。
接下来会讲解提升和闭包两个概念。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
猜你喜欢:- 图解词法作用域与作用域链
- javascript作用域之块级作用域
- javascript静态作用域和动态作用域
- JavaScript系列之作用域和作用域链
- 【7】JavaScript 函数高级——作用域与作用域链
- 深入学习js之——词法作用域和动态作用域
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。