JavaScript难点系列:作用域
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JavaScript难点系列:作用域相关的知识,希望对你有一定的参考价值。
深入了解js这门语言后,才发现它有着诸多众所周知的难点(例如:闭包、原型链、内存空间等)。有的是因为js的设计缺陷导致的,而有的则是js的优点。不管如何,总需要去学会它们,在学习过程中我觉得只看别人的文章并不能做到深刻理解,所以我决定写这一系列的文章来记录我所学习到的知识点,也方便自己以后回顾,如有写错的地方欢迎指正。
废话不多说,马上进入正题!
函数作用域
有句人人皆知的江湖传言:“javascript没有块级作用域”。当然这是ES6之前的事了,我们需要知道的是JS除了全局作用域外就是函数作用域了。JS中的作用域和this指定机制恰好相反,它是在函数创建时就确定的,而不是调用的时候。
来看一段简单的代码
function foo() {
var a = 100
function bar() {
var a = 200
}
}
上面这段代码分别形成了全局作用域、foo作用域和bar作用域。而且作用域有上下级的关系(也可以理解为包含关系),这个上下级关系的确定就看函数是在谁的作用域下创建(不是执行)。上述代码中,foo作用域下创建了bar函数,那么foo作用域就是bar作用域的上级。
静态作用域
作用域分两种,一种是动态作用域(函数的作用域在函数调用的时候才决定),一种是静态作用域(函数的作用域在定义时就已经决定,也叫词法作用域)。JS采用的是静态作用域,来看个例子就明白了。
var a = 1
function foo() {
console.log(a)
}
function bar(f) {
var a = 2
(function() {
f()
})()
}
bar(foo) // 1
坊间一直有种说法,说是查找变量时如果在该函数作用域找不到,就去它的父级作用域找。其实这种说法是很容易让人产生歧义的。我们从静态作用域的角度去分析,foo函数的作用域在它定义时就已经确定了,所以foo作用域的上级作用域是全局作用域,当foo函数在bar函数内被调用时,它发现找不到变量a,于是去上级作用域也就是全局作用域寻找,自然结果就是a = 1。
以上是关于JavaScript难点系列:作用域的主要内容,如果未能解决你的问题,请参考以下文章