記錄學習 -- ES6 中不存在變數提升 / 預編譯:
阿新 • • 發佈:2020-12-31
ES6 中不存在變數提升:
在 ES6 中我們可以使用 let
和 const
來命名變數,他們有一些特性:
要記住,ES6 語法,程式碼在執行之前,會進行記錄,然後進行檢測,如果有重複的就報錯;
1,切斷了 全域性變數 和 window
屬性的對映機制;
console.log(window.a) // undefined
let a = 12;
console.log(window.a) // undefined
2,不存在變數提升;
console.log(a) // => 報錯,沒有定義就使用;Cannot access 'a' before initialization
let a = 12;
console.log(a) // => 12
3,不能重複宣告,不管之前建立的變數是用何種方式宣告的,var
或者是 window.xx
;
a = 21
/*
這樣宣告就是 window 的屬性,但是在程式碼執行之前,瀏覽器會檢測當前的作用域,看看是否有使用 let 宣告的變數,如果有的話,程式碼執行時,還沒有執行到使用 let 宣告的地方,在他之前使用該變數,就會報錯;
*/
let a = 12;
console.log(a)
4,實現, ES6 有一種機制,我們可以把它稱為 “檢測機制”,在 程式碼執行之前,會在當前作用域進行檢測,記錄建立的變數;程式碼執行時,然後遇到之前 記錄的變數重複聲明瞭,就直接報錯;
b = 12
console.log(b) // => 12
a = 32; // Uncaught ReferenceError: Cannot access 'a' before initialization
console.log(a)
let a = 12;
console.log(a)
/*
程式碼執行之前,進行檢測,記錄使用 let 等宣告的變數,然後執行程式碼;
執行到 console.log(b) 時,可以
執行到 a = 32; 時, 報錯,沒有初始化就使用了!
程式碼並不是 執行當前行,然後檢測後面的,不是說 a = 32, 沒錯,然後執行到 let a = 12 就報錯,說前面有 a了, 當前行會報錯這樣,不是的,在程式碼執行之前,會有一次 檢測記錄的,遇到 a = 32 就直接報錯了,因為 瀏覽器有記錄的。
*/
在 ES6 之前,使用 typeof 判斷一個變數的型別,如果沒有定義的變數,不會報錯,而是輸出 undefined
console.log(typeof a); //=> undefined
console.log(a); // 報錯,a 沒有定義
很明顯不正常,在 ES6 中修改了這個 bug
console.log(typeof a) // 報錯
let a
console.log(a)