理解作用域 (你不知道的Javascript)

164 阅读1分钟

LHS 与 RHS (左值与右值)

LHS:赋值操作的左侧。

RHS:查找某个值。

function foo(a) {
  var b = a
	return a + b
}
foo(2)

问以上代码有几处LHS,几处RHS查询?

  • foo(2) 查找 foo() [RHS] , a = 2 [LHS]
  • var b = a 赋值b [LHS] , 查找 a [RHS]
  • return a + b 查找 a [RHS] 和 b [RHS]

当执行 RHS 查询时,查询失败则报 ReferenceError 。

词法作用域

词法作用域 vs 动态作用域

词法作用域就是定义在词法阶段的作用域。

Javascript 采用的是词法作用域,函数的作用域在函数定义时就决定了,

而动态作用域则是,函数的作用域在函数调用阶段才决定。

var b = 1
function foo(){
	var b = 2
  	bar()
}

function bar() {
	console.log(b)
}

foo()

执行 bar 函数,先从 bar 函数内部查找是否有局部变量 b ,如果没有,就根据书写的位置,查找上一层的代码,也就是 b = 1,所以会打印 1。

Javascript 中的 eval(...) 函数可以接受一个字符串为参数,并将其中的内容视为好像在书写时就存在于程序中这个位置的代码。

也就是说,可以在你写的代码中用程序生成代码并运行,就好像代码是写在那个位置的一样。

不用eval, 它动态的修改了词法作用域,导致 JS 引擎在编译阶段发现代码里有它后无法进行优化,导致代码性能很差。