天天看點

《深入了解JavaScript》——1.14 對象和構造函數

本節書摘來自異步社群《深入了解javascript》一書中的第1章,第1.14節,作者: 【美】axelrauschmayer(羅徹麥爾)譯者: 王玉林 , 杜歡 , 莊婷婷 , 章子鵬,更多章節内容可以通路雲栖社群“異步社群”公衆号檢視。

本節涵蓋了javascript兩種基礎的面向對象機制:單一對象和構造函數(類似其他語言中對象的工廠方法)。

1.14.1 單一對象

和所有的值一樣,對象也具有屬性。你可以認為對象是一組屬性的集合,事實也是如此,每個屬性都是一個(鍵,值)對。鍵名都是字元串,而值可以是javascript的任意值。

在javascript中,可以直接通過對象字面量去建立普通對象:

  

《深入了解JavaScript》——1.14 對象和構造函數

上述對象具有name和describe兩個屬性。你可以擷取(get)以及設定(set)這些屬性:

《深入了解JavaScript》——1.14 對象和構造函數

以函數作為值的屬性被稱為方法,如describe。它們使用this對調用它們的對象進行引用:

《深入了解JavaScript》——1.14 對象和構造函數

使用in運算符檢查屬性是否存在:

《深入了解JavaScript》——1.14 對象和構造函數

如果讀取一個不存在的屬性,會得到undefined。是以,之前的兩個檢查可以這樣執行:

《深入了解JavaScript》——1.14 對象和構造函數

使用delete運算符移除屬性:

  .

《深入了解JavaScript》——1.14 對象和構造函數

1.14.2 任意屬性名

屬性的鍵名可以是任何字元串。迄今為止,我們見到過對象字面量中的屬性名和點運算符後的屬性名。然而,隻有當它們是辨別符的時候才可以這樣使用(參見1.3.3“辨別符與變量名”)。如果想用其他的字元串作為屬性名,則必須将它們用引号引起來,再通過對象字面量和方括号來擷取或設定這個屬性:

《深入了解JavaScript》——1.14 對象和構造函數

方括号可以用來動态計算屬性鍵名:

《深入了解JavaScript》——1.14 對象和構造函數

1.14.3 提取方法

如果對方法進行提取,則會失去與對象的連接配接。就這個函數而言,它不再是一個方法,this的值也會是undefined(在嚴格模式下)。

看如下示例,先回到之前的jane對象:

《深入了解JavaScript》——1.14 對象和構造函數

我們要從jane對象中提取describe方法,将它指派給變量func,然後對它進行調用。你會發現,它不能正常運作:

《深入了解JavaScript》——1.14 對象和構造函數

處理這個問題的解決方案可以使用bind()方法,所有函數都支援。它會建立一個this總是指向給定值的新函數:

《深入了解JavaScript》——1.14 對象和構造函數

1.14.4 方法中的函數

所有函數都有其特殊的this變量。如果在方法中有嵌套函數,這可能會不太友善,因為在嵌套函數内部不能通路方法中的this變量。下面這個例子展示了調用foreach并結合一個函數來周遊數組:

《深入了解JavaScript》——1.14 對象和構造函數

調用loghitofriends會産生一個錯誤:

 

《深入了解JavaScript》——1.14 對象和構造函數

讓我們來看看這個問題的兩種解決方法。第一種,我們可以将this儲存在不同的變量中:

《深入了解JavaScript》——1.14 對象和構造函數

第二種,利用foreach的第二個參數,它可以給this指定一個值:

《深入了解JavaScript》——1.14 對象和構造函數

函數表達式在javascript中通常被當作函數調用中的參數來使用。在這些函數表達式中引用this時要特别小心。

1.14.5 構造函數:對象工廠

到現在為止,javascript對象字面量表現出的那種類似于其他語言中映射表/字典的印象,可能會使你覺得javascript對象僅僅是字元串到值的映射。然而,javascript對象也支援真正的面向對象:繼承。本節不會去完全解釋javascript的繼承是如何工作的,而會展示一種簡單的模式讓你快速上手。想了解更多詳情,請檢視第17章。

除了“真正的”函數和方法,函數在javascript中還扮演了另外一個角色:如果用new運算符來調用的話,它們将變成構造函數即對象工廠。構造函數就是這樣簡單地模拟了其他語言的類。按照慣例,構造函數的名稱以大寫字母開頭。例如:

《深入了解JavaScript》——1.14 對象和構造函數

可以看到構造函數包含兩部分。第一部分,point函數設定執行個體資料。第二部分,point.prototype屬性包含一個帶有方法的對象。第一部分裡的執行個體資料是特定于每一個執行個體的,而之後的方法資料則是對所有執行個體共享的。

可以通過new運算符來使用point:

《深入了解JavaScript》——1.14 對象和構造函數

p是point的一個執行個體:

《深入了解JavaScript》——1.14 對象和構造函數

繼續閱讀