1. 物件導向與 new
關鍵字
JavaScript 是基於 原型 (Prototype) 的物件導向語言,而非典型的 類別 (Class) 為基礎的語言。但 ES6 之後,JavaScript 引入了 class
語法,使其更接近傳統的物件導向語言,如 Java 或 C++。
在 JavaScript 中,new
關鍵字用於建立物件,並且會執行以下步驟:
- 建立一個新的空物件。
- 設定該物件的
__proto__
指向建構函式 (Constructor) 的prototype
。 - 執行建構函式內的程式碼,並將
this
綁定到新建立的物件。 - 如果建構函式沒有明確返回物件,則回傳該新物件。
範例:
function Person(name, age) { |
2. __proto__
vs prototype
在 JavaScript 中,__proto__
和 prototype
是兩個不同的概念。
prototype
prototype
是建構函式的一個屬性,它是一個物件,當我們使用 new
建立物件時,該物件的 __proto__
會指向 prototype
。
範例:
function Animal(name) { |
__proto__
__proto__
是物件的內部屬性,指向該物件的原型,即 prototype
。
範例:
console.log(dog.__proto__); // Animal.prototype |
關鍵點整理:
prototype
是函式的屬性。__proto__
是物件的屬性,指向它的prototype
。Object.prototype
是所有物件的最終原型。
3. class
關鍵字
ES6 之後,JavaScript 引入了 class
語法,使物件導向的寫法更直覺。
定義類別 (Class)
class Car { |
等同於 ES5 的寫法:
function Car(brand) { |
優勢:
class
提供更簡潔的語法。- 更貼近傳統物件導向語言的語法風格。
constructor
方法負責初始化物件。- 方法定義在
prototype
上,並不會重複創建。
4. extends
繼承
在 ES6 之前,我們使用 Object.create()
或手動設定 prototype
來實現繼承。
傳統的原型繼承
function Animal(name) { |
使用 class
的繼承
class Animal { |
關鍵點:
extends
用於建立類別的繼承。super(name)
呼叫父類別的constructor
,確保this
正確初始化。- 子類別可以新增自己的方法。
5. 物件導向開發的最佳實踐
- 使用
class
提供更清晰的結構。 - 使用
extends
來建立繼承關係,並呼叫super()
確保正確初始化。 - 方法定義於
prototype
來減少記憶體浪費。 - 理解
__proto__
和prototype
之間的關係,以便更好地管理原型鏈。 - 避免過度使用繼承,適時使用組合 (Composition) 來降低耦合度。
6. 總結
特性 | 傳統原型 (Prototype) | ES6 class |
---|---|---|
建立物件 | new Function() |
new Class() |
方法定義 | Function.prototype.method = function() {} |
直接定義於 class |
繼承 | Object.create() + call() |
extends + super() |
this 綁定 |
需要 call() 或 bind() |
super() 自動綁定 |
JavaScript 的物件導向概念提供了靈活的方式來組織程式碼,掌握 prototype
、class
、extends
和 super()
,可以幫助開發者寫出更具可讀性與可維護性的程式碼。