07_javascript作用域與作用域鏈
阿新 • • 發佈:2018-12-14
作用域
理解
就是一塊"地盤", 一個程式碼段所在的區域
它是靜態的(相對於上下文物件), 在編寫程式碼時就確定了
分類
全域性作用域
函式作用域
沒有塊作用域(ES6有了)
作用
隔離變數,不同作用域下同名變數不會有衝突
//ES5 沒塊作用域 if(true) { var c = 3 } console.log(c) //3 var a = 10, b = 20 function fn(x) { var a = 100, c = 300; console.log('fn()', a, b, c, x) //fn() 100 20 300 10 function bar(x) { var a = 1000, d = 400 console.log('bar()', a, b, c, d, x) } bar(100)//bar() 1000 20 300 400 100 bar(200)//bar() 1000 20 300 400 200 } fn(10)
作用域與執行上下文
區別1
全域性作用域之外,每個函式都會建立自己的作用域,作用域在函式定義時就已經確定了。
而不是在函式呼叫時
全域性執行上下文環境是在全域性作用域確定之後, js程式碼馬上執行之前建立
函式執行上下文環境是在呼叫函式時, 函式體程式碼執行之前建立
區別2
作用域是靜態的, 只要函式定義好了就一直存在, 且不會再變化
上下文環境是動態的, 呼叫函式時建立, 函式呼叫結束時上下文環境就會被釋放
聯絡
上下文環境(物件)是從屬於所在的作用域
全域性上下文環境==>全域性作用域
函式上下文環境==>對應的函式使用域
作用域鏈
理解
多個上下級關係的作用域形成的鏈, 它的方向是從下向上的(從內到外) 查詢變數時就是沿著作用域鏈來查詢的
查詢一個變數的查詢規則
在當前作用域下的執行上下文中查詢對應的屬性, 如果有直接返回, 否則進入2 在上一級作用域的執行上下文中查詢對應的屬性, 如果有直接返回, 否則進入3 再次執行2的相同操作, 直到全域性作用域, 如果還找不到就丟擲找不到的異常
var a = 1 function fn1() { var b = 2 function fn2() { var c = 3 console.log(c) //3 console.log(b) //2 console.log(a) //1 console.log(d) //d is not defined } fn2() } fn1()
面試題
面試題1
var x = 10;
function fn() {
console.log(x);
}
function show(f) {
var x = 20;
f();
}
show(fn);
//10
面試題2
var fn = function () {
console.log(fn)
}
fn()
/*
ƒ () {
console.log(fn)
}
* */
var obj = {
fn2: function () {
console.log(fn2)
}
}
obj.fn2()
// Uncaught ReferenceError:
// fn2 is not defined at Object.fn2