變數提公升(hoisting):使用 var 關鍵字宣告的變數,無論其實際宣告位置在何處,都會被視為宣告於所在函式的頂部(如果宣告不在任意函式內,則視為在全域性作用域的頂部)。
特點:
(1)同名變數忽略
var foo;
var foo; //忽略
var foo; //忽略
…… //忽略
(2)同名函式覆蓋
function
fly()
function
fly() //覆蓋
fly(); //'eagle'
(3)變數函式同名
var bar;
function
bar();
var bar;
function
bar();
var bar;
typeof bar; //'function'
bar(); //'bar2'
個人理解:按宣告的順序提公升,無論第乙個是變數宣告還是函式宣告都會忽略後續的同名var宣告,並被後續的同名function覆蓋,結果是函式宣告有效。(注:《you don't know js》一書中說函式與變數同名時,函式有更高的優先順序,同名變數被當做重複宣告忽略。)
(4)只提公升宣告
只有宣告本身會被提公升,而賦值或其他運算邏輯會留在原地
將變數作用域限制在當前**塊中。
共同點:
(1)禁止重複宣告;
(2)tdz(temporal dead zone),使用 let 或 const 宣告的變數,在達到宣告處之前都是無法訪問的,試圖訪問會導致乙個引用錯誤;
(3)建立塊級作用域,只在宣告所在的塊級作用域存在,使變數在必要位置準確宣告;
(4)不繫結到全域性物件;
不同點:
(1)const 宣告變數時必須同時進行初始化,而 let 不必要;
(2)const 宣告的變數值不可改變(如果是常量物件,其包含的值可以修改),而let無限制;
由於es6之前缺少塊級作用域,乙個關於迴圈的問題總是被提及。
var arr = ;
for (var i = 0;i < 10;i++) )
}arr.foreach(function
(func));
//或者別的形式
for (var j = 0;j < 10;j++) ,j * 1000);
}
初學時之所以會成為乙個問題,核心在於我們想要每層迴圈捕獲到當時的迴圈變數的值,而事實上我們用到的是共享作用域的 i 或者 j ,是終止迴圈時變數的值;換句話說,我們缺少塊級作用域。
因此我們自然想到了 立即執行函式(iife)來解決此問題
for (var j = 0;j < 10;j++) ,k * 1000);
})(j);
}
那麼es6的解決方法是什麼呢?
for (let j = 0;j < 10;j++) ,j * 1000);
}
那麼 let 實現的原理是什麼?此處能不能換成 const ?下面來繼續分析,執行過程可拆解成如下
,i *1000)
}}
所以,let 的變數除了作用域是在 for 區塊中,而且會為每次迴圈執行建立新的詞法環境(lexical environment),拷貝所有的變數名稱與值到下個迴圈執行。const 宣告的變數值不可修改,因此這裡不可以用 const。
更進一步,我們看 let 和 const 在 for…in 與 for…of 中的表現。
var funcs = ,
object = ;
// 不會導致錯誤
for (const key in object) );
} funcs.foreach(function
(func) );
const 與 let 能夠在 for-in 與 for-of 迴圈內工作,是因為迴圈為每次迭代建立了乙個新的變數繫結,而不是試圖去修改已繫結的變數的值
總是使用 const 宣告變數,明確知道變數需要更改的時候使用 let 宣告變數,不使用 var 宣告變數。
理論依據:大部分變數在初始化之後都不應當被修改,因為預期外的改動是 bug 的源頭之一。
ES6學習筆記 塊級繫結
使用var關鍵字宣告的變數,無論其實際宣告位置在何處,都會被視為宣告於所在函式的頂部 如果宣告不在任意函式內,則被視為在全域性作用域的頂部 這就是所謂的變數提公升 hoisting 後台實際上會轉化成這樣 value變數的宣告被提公升到了頂部,而初始化工作則保留在原處。這以為著在else分支valu...
es6 塊級作用域用法
iife 寫法 function 塊級作用域寫法 塊級作用域的出現,實際上使得獲得廣泛應用的立即執行函式表示式 iife 不再必要了。function f function f 上面 在 es5 jscript不支援塊級作用域環境中執行,會得到 i am inside 因為在 if內宣告的函式f會被...
ES6的塊級作用域
為什麼要使用塊級作用域?1.在預編譯階段,變數的宣告會被提公升到作用域頂部,而初始化操作依舊留在原處執行,在該作用域中未定義變數的地方也能訪問到該變數,但是此時變數尚未初始化,所以其值為undefined,為此es6引入塊級作用域來強化對變數生命週期的控制 塊級宣告 1.塊級作用域用於宣告在指定塊的...