1. 程式人生 > >ES6中的常量宣告——const關鍵字

ES6中的常量宣告——const關鍵字

const宣告常量

之前一直沒有仔細想過const這個常量宣告,有時候遇到了明顯的問題,竟然忽略了過去,最終的結論是——const宣告的常量是不能改變的,這句描述是並不太準確的。

很多時候,常量宣告用來宣告一個固定的不變的資料,比如圓周率PI。

const PI = 3.14;
PI; // 3.14
PI = 3; // TypeError: Assignment to constant variable.

測試結果很顯然的說明通過const關鍵字宣告的識別符號是無法改變值的。

但是很多時候,也經常會在各種程式碼中看到 const obj = {} 類似這樣的物件常量,結果這樣明明也是常量宣告的資料,卻依然可以通過 obj.x = 1

這樣的語句給該物件新增屬性或方法。如此,const關鍵字宣告的常量的值無法改變這句話就變得不再可信了。

於是有了猜測,const關鍵字宣告的常量的指標不能發生改變。

const obj = {};
obj.n = 123;
obj; // { n: 123 }
obj = { x: 1 }; // TypeError: Assignment to constant variable.

在物件中新增屬性,是在堆中該物件的資料裡新增資料,而沒有改變obj中存放的指向該物件的地址,所以是可以執行成功的,而對obj重新賦值的操作則改變了obj的指標指向,故而操作失敗,丟擲錯誤。

對於基本型別也是同樣,因為基本型別的資料直接就存放在棧中,常量名直接指向這個地址上的資料,一旦改變值,就會導致指標地址發生改變,所以造成了無法改變值的假象。

因為本人是個新人,對自身能力不夠自信,所以還查找了下其他的資料,在阮一峰老師寫的《ECMAScript6 入門》中的const命令 中“本質”有講:

const實際上保證的,並不是變數的值不得改動,而是變數指向的那個記憶體地址不得改動。對於簡單型別的資料(數值、字串、布林值),值就儲存在變數指向的那個記憶體地址,因此等同於常量。但對於複合型別的資料(主要是物件和陣列),變數指向的記憶體地址,儲存的只是一個指標,const只能保證這個指標是固定的,至於它指向的資料結構是不是可變的,就完全不能控制了。因此,將一個物件宣告為常量必須非常小心。

看到這些,心裡終於有譜了,趕緊記錄下來。