全域性變數,個人理解全域性變數就是全域性物件window的屬性
var a = 5 // 宣告一個全域性變數
console.log(window.a) // 5
複製程式碼
1.變數作用域
javaScript的全域性變數的作用域,顧名思義作用域就是全域性,而函式的引數跟區域性變數的作用域在函式體內。
如果兩個變數重名,一個變數是全域性變數,一個是區域性變數,優先順序是 區域性變數>全域性變數
var a = 1 // 宣告全域性變數
function fuc() {
var a = 2 // 區域性變數
return a
}
console.log(fuc()) // 2複製程式碼
如果在函式內宣告變數沒有帶var,會被當作全域性變數,也叫隱式宣告
function fuc() {
var a = 2 // 區域性變數
return a
}
console.log(a) // a is not defined複製程式碼
function fuc() {
a = 2 // 沒有var,此時a是全域性變數
return a
}
console.log(a) // 2複製程式碼
2.函式作用域
javaScript變數的作用域,與java等語言不同的是,在變數宣告的程式碼塊之外是不可見的,簡稱“塊級作用域”
function fuc(){
console.log(num) // 輸出未定義的變數 會報錯
}
fuc() // num is not defined複製程式碼
function fuc(){
console.log(num) // 不報錯, 輸出undefined,因為num在函式體內有定義
var num = 5
console.log(num) // 5
}
fuc()
//由於變數提升,上面程式碼等價於
function fuc(){
var num
console.log(num) // undefined
num = 5
console.log(num) // 5
}
fuc()
複製程式碼
3.作用域鏈
javaScript的函式是允許巢狀的,就是在一個函式內部宣告另一個函式,程式碼如下
function A(){
var num = 5
function B() {
var b = 2
}
}
複製程式碼
執行A函式的時候,會建立A函式的作用域,B函式在建立的時候會引用A的作用域
執行B函式的時候會引用函式A的作用域,由所謂的函式作用域的巢狀形成了函式作用域鏈。
在自身如果找不到該變數的時候,就會沿著作用域向上查詢,直至在全域性作用域找不到時丟擲錯誤
作用域題目
- js內部作用域可以訪問外部,但外部不能訪問內部
var a = 10
function aaa () {
alert(a) // 呼叫順序3,內部沒有a變數,沿著作用域鏈向上尋找,在找到全域性變數a =10
}
function bbb () {
var a = 20
aaa() // 呼叫順序2
}
bbb() // 呼叫順序1 結果為10複製程式碼
- 不用var定義變數,會預設為全域性變數
function aaa(){
var a=b=10
}
aaa()
alert(a) // 報錯
alert(b) // 10
//上面aaa()的程式碼等價於下面
var b = 10
function aaa() {
var a = b
}複製程式碼
- 尋找變數是就近原則,沿著作用域鏈往上找,變數的宣告會被提升至頂部,賦值會留在原地
function aaa () {
alert(a)
var a = 20
}
aaa() // undefined 此題與上面第二點的例子一樣複製程式碼
- 同名的全域性變數跟區域性變數,區域性變數優先順序大於全域性
var a = 10
function aaa () {
alert(a)
var a = 20
}
aaa() //結果為:undefined
//此程式碼等價於
var a = 10
function aaa () {
var a
alert(a) //undefined
a = 20
}
aaa() //結果為:undefined複製程式碼
- 如果形參與區域性變數同名時,優先順序一樣
var a = 10
function aaa (a) { // 函式傳入形參 a
alert(a)
var a = 20
}
aaa(a) // 結果為: 10複製程式碼
var a = 1
var a // 這裡的var a 是一個重複定義,變數只有定義後未賦值才會輸出undefined,
這裡JS引擎對重複定義的規定是:以最近的變數賦值作為變數在執行時的值
所以var a相當於無效
console.log(a) // 1
複製程式碼
- 變數修改的時候,另一個變數會跟著變化,但是重新定義時,另一個不跟隨變化
var a=[1,2,3]
var b = a
b.push(4)
alert(a) // 結果為[1,2,3,4] 當b改變的時候a也發生了改變
當b重新被賦值的時候 a不會改變.示例:
var a = [1,2,3]
var b = a
b = [1,2,3,4]
alert(a) // 結果為 [1,2,3]
複製程式碼