ES6中的var let const應如何選擇


javascript世界里面的每個人都在說有關ECMAScript 6 (ES6,也稱作ES 2015)的話題,對象的巨大變化 ( 類 , super() , 等), 函數 (默認參數等), 以及模塊 (導入/導出), 但 很少有人關注 變量以及如何定義。事實上,還是有一些關注,但是可能關注點並非正確。我最近參加了英國jQuery會議,在會議上 Dave Methvin 發表了一場關於 ES6簡介 的演講,演講內容包含了很多關於 let 和 const 的內容。

通過這篇文章,我想介紹 var 的這兩個不同的關鍵字,以及它們在定義和使用上的區別。並且更重要的,我要確定哪些人正在考慮在ES6中使用聲明變量的新標准。基本概念是 let 應該立刻取代 var 作為定義的關鍵字。事實上,按照一些案例, var 簡單的說不應該再在新代碼中使用。 const 關鍵字用在那些永遠不會改變的變量申明, let 用在其他變量申明上。

用 let 取代 var

這個代碼示例一看上去似乎比較有戲劇性,但是對我們思考 let 和 var 的差異來說,顯得不會太多。 var 在離它最近的父函數內創建了一個變量的作用域 let 在它最近的塊級中創建作用於,這些塊包括 for 循環, if 語句以及其他塊。

 

 1 function foo ( ) {
 2 
 3 console . log ( x ) ;
 4 
 5 console . log ( y ) ;
 6 
 7 var x = 1 ;
 8 
 9 if ( x === 1 ) {
10 
11 let y = 2 ;
12 
13 }
14 
15 console . log ( y ) ;
16 
17 }
18 
19 foo ( ) ;
20 
21 console . log ( x ) ;

 

在這個例子中,我們創建了一個 foo 的函數(以及變量作用域),並且稍后我們調用它。最后一個 console.log() 語句預期會產生一個 ReferenceError ,因為 x 只在 foo() 中定義(作用域)。因為變量提升,第一個console預計將被正常執行。在這個示例中, x 是 undefined 。第二個console預計更加有趣。事實上,兩個 log(y) 都將出錯,因為 let 比 var 的作用於更加嚴格。 y 變量 只存在於 if 塊里面,不在任何其他地方。Dave Methvin稱 let 之前的區域叫做“ 臨時死亡區 。”

希望這個例子能夠向你展示 let 的特性,但是你或許會說有時候你實際上想 有一個 函數范圍作用域的變量。沒問題,簡單的說在函數頂部創建這個變量就好了。

 1 function foo ( x ) {
 2 
 3 let y <s4>=</s4><s5> </s5><s6>2</s6><s7>;</s7>
 4 
 5 if ( x === 1 ) {
 6 
 7 y = 2 ;
 8 
 9 }
10 
11 console . log ( y ) ;
12 
13 }
14 
15 foo ( ) ;
16 
17 console . log ( y ) ;

 

上面的函數在函數頂部定義了 y ,因此相比第一個例子,賦予了它更大范圍的作用域。我們可以看見 y 在這個函數任意地方都可以訪問,但是在外面不行,因此最后一個 console.log(y) 語句依然會產生 ReferenceError 。在我們介紹 const 前, 讓我們重申一下這點:在ES6中 let 應該完全取代 var 。上面的示例向你展示了 let 十分強大,並且和 var 一樣擁有十分多的靈活性。我 並不是第一個這樣說的人 但是我現在是這種想法的信仰者。

常量索引,不是值

在ES6中另外一個定義變量的關鍵字是 const , 但是它經常被誤會為一個“常量”。在ES6中, const 代表一個值的 常量索引 (事實上絕大多數語言都提供這樣的功能)。換句話說,變量名字在內存中的指針不能夠改變,但是指向這個變量的值 可能 改變。

這里有一個簡單的例子。在下面的例子中我們可以創建一個擁有常量索引的數組變量。我們在之后添加值到這個數組中並不改變這個索引,一切都可以運行起來:

 1 const names = [ ] ; 2 3 names . push ( “Jordan” ) ; 4 5 console . log ( names ) ; 

但是,如果我們嘗試修改變量索引到一個新的數組——即使是和現在內容一樣的數組——我們將獲得一個SyntaxError (“Assignment to constant variable”):

const names = [ ] ; names = [ ] ; // Error!

當然,如果你擁有一個指向string或者number的 const ,當然這里就不會有任何可以修改的值。所有String和Number的方法返回 新的 值(對象)。

最后一個關於使用 const 的注意事項是參考 let 的新作用域規則!那意味着我們應該在我們的代碼中使用 let 和 const 完全代替 var 。事實上,依然有很多人支持作為沒有涉及到的遺留代碼只“允許”使用 var 的想法當一個程序員在一個文件中更新一些代碼,他們應該 (並且可能)將所有 var 語句更新為適當的有適當作用域的 let 或者 const 。

但是只適配ES6…

那是對的。新的 let 和 const 關鍵字在ES5中不生效,並且因此在絕大多數可執行環境中也不生效。但是,通過類似 Babel 優秀的編譯器, 我們可以將我們寫的ES6 JavaScript代碼編譯為可在瀏覽器環境中執行的ES5代碼。

對於開發Node.js (以及io.js)的程序員來說,幸運但是我們不需要考慮某人使用什么瀏覽器來執行我們的代碼。如果你正在使用 Node v0.12 (你正在使用,對嗎?), 你可以通過兩個小修改來使用這些新功能。第一步,你必須使用“harmony”功能來運行你的代碼(最初ES6開發代碼是“harmony”):

~ $ node — harmony / path / to / script

第二個改變是任何使用 let 或 const (或其它ES6功能)的代碼必須使用嚴格模式。為了實現這個,簡單的將 "use strict;" 放在每個模塊最頂部。另一方面,你可以在CLI中使用 --use-strict 標志,但這似乎有些多余。

在io.js中你不必需要 --harmony 標志,因為所有這些功能都在代碼中集成。但是,你還是必須使你代碼為嚴格模式。再次說明,很簡單的通過在你每隔模塊文件頂部加上 "use strict"; 語句來實現。

你在使用io.js嗎?希望StrongLoop支持它嗎? 我們已經支持了 !除了 StrongLoopAPI平台 已經能在io.js上運行,我們也提供給 我們的顧客在io.js上運行。

現在出去,並創建一個更好的變量聲明工作流程!

 

原文鏈接 http://www.codesec.net/view/165972.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM