當前位置:
首頁 > 最新 > let 聲明會提升嗎?

let 聲明會提升嗎?

昨天我上課的時候跟飢人谷的學生講了《let 聲明的五個特點》,其中一個就是「let 聲明會提升到所在塊的頂部」,然而今天早上有個學生就問我了:

MDN 上說 let 不會提升,為什麼你說 let 會提升呢?

當時我心裡一方:難道我講錯了?

於是我看了 MDN 英文版的原文,發現寫的也是:

In ECMAScript 2015, let do not support Variable Hoisting, which means the declarations made using "let", do not move to the top of the execution block.

看來我真的錯了?於是我繼續翻看 ECMA-262.pdf,發現了兩處地方支持我的論點。

首先是 13.3.1 Let and Const Declarations

let and const declarations define variables that are scoped to the running execution context s LexicalEnvironment. The variables are created when their containing Lexical Environment is instantiated but may not be accessed in any way until the variable s LexicalBinding is evaluated.

這說明即使是 block 最後一行的 let 聲明,也會影響 block 的第一行。這就是提升(hoisting)。

以及 18.2.1.2 Runtime Semantics: EvalDeclarationInstantiation( body, varEnv, lexEnv, strict)

The environment of with statements cannot contain any lexical declaration so it doesn t need to be checked for var/let hoisting conflicts.

這句話從側面證明了 let hoisting 的存在。

所以,我就把 MDN 的英文版和中文版給糾正過來了:

在 ECMAScript 2015中, let 也會提升到語句塊的頂部。但是,在這個語句塊中,在變數聲明之前引用這個變數會導致一個 ReferenceError的結果

希望被之前 MDN 某個版本誤導的同學周知。

總結一下:

let 聲明會提升到塊頂部

從塊頂部到該變數的初始化語句,這塊區域叫做 TDZ(臨時死區)

如果你在 TDZ 內使用該變數,JS 就會報錯

我可沒說 TDZ 跟 hoisting 等價!

更新:

有些同學還是認為 let 不會提升,試試理解下面的代碼:

let a = 1 { a = 2 let a }

如果 let 不會提升,那麼 a = 2 就會將外面的 a 由 1 變成 2 啊。

運行發現 a = 2 報錯:Uncaught ReferenceError: a is not defined

這說明上面的代碼近似近似近似近似近似近似地可以理解為:(注意看注釋中的 TDZ,早知道我就不寫代碼了,有些人看代碼不看注釋)

let a = 1 { let a // TDZ 開始的地方就是這裡 start a TDZ a = 2 // 由於 a = 2 在 TDZ 中,所以報錯 a // TDZ 結束的地方就是這裡 end a TDZ }

所以,let 提升了。

完。

喜歡這篇文章嗎?立刻分享出去讓更多人知道吧!

本站內容充實豐富,博大精深,小編精選每日熱門資訊,隨時更新,點擊「搶先收到最新資訊」瀏覽吧!


請您繼續閱讀更多來自 推酷 的精彩文章:

用代碼寫靜態表格
如何設計合理友好的錯誤提示?
Spring boot學習
perseus:基於 Mybatis+Spring 的讀寫分離方案
深度學習思考

TAG:推酷 |

您可能感興趣

她離開了所屬社,但是同時聲明會保持女團的活動!
范冰冰任由謠言滋生無所作為?知情人:發聲明會被落井下石,一直默默調查取證