JavaScript Class
In Object-oriented programming, a class is an extensible program-code-template for creating objects, providing initial values for state(member variables) and implementations of behavior(member functions or methods).class 是一種可以拓展的編程模板,用來創建對象(object),提供狀態初始值(變量)和行為實現(函數或方法)。
JavaScript 雖然具有物件導向程式語言的特性,但與 Java、C++ 等以類別為基礎的程式設計規範不同,JavaScript 是一種以原型(prototype-based)為基礎的語言。
由於開發上經常需要創建許多相似類型的對象,傳統的 JavaScript 寫法,可以用構造函數(Constructor)和 operator new
來達成這個使用目的,但在 ES6 中有一個更進階的用法叫做 Class
。
ECMAScript 6 中引入了類別 (class) 作為 JavaScript 現有原型程式(prototype-based)繼承的語法糖。語法糖可以讓現有語法操作變得更容易。類別(class)語法並不是要引入新的物件導向繼承模型到 JavaScript 中,而是提供一個更簡潔的語法來建立物件和處理繼承。
Class 允許使用更簡潔的結構語法來定義 prototype-based 的類別。在 prototype-based 類別中,所有 methods 都存在 prototype 屬性中,藉以與其他延伸出去的類別共用,如此可以節省 memory 空間。
比較傳統原型繼承的寫法和使用 class 的寫法會發現;class 省略了 prototype chaining 並且整個 class 的宣告定義集中描述在 class 區塊內,幫助讀者了解這段程式的作用範圍,使 class 的目的更為清楚。
Constructor 構造函數
- 是一種常規函數,函數名稱首字必須大寫
- 創建時必須使用
new
來操作 - 需在
prototype
物件上定義方法 - 示範:
1
2
3
4
5
6
7
8
9
10
11
12
13
14function User(name) {
this.name = name;
this.isAdmin = false;
}
User.prototype.sayHi = function() {
console.log(this.name);
}
let user = new User("Jack"); // 創建一個 User Constructor
alert(user.name); -> Jack
alert(user.isAdmin); -> false
user.sayHi() -> Jack
當一個函數作為
new User(...)
執行時,它執行以下步驟:- 一個新的空對像被創建並分配給
this
。 - 函數體執行。通常它會修改
this
,為其添加新的屬性。 - 返回
this
的值。
所以new User("Jack")
的结果是相同的對象
Class 用法與特色
- 使用
constructor()
建構子來定義初始狀態,而且創建時也必須使用new
來操作。
建構子(constructor)方法是一個特別的方法,用來建立和初始化一個類別的物件,一個類別只能有一個建構子(constructor)。
Class 的constructor()
函數是默認的 method,即使沒有寫出來也會自動生成一個默認的空構造函數,並加入到class.prototype
上。
class syntax:1
2
3
4
5
6
7
8
9
10
11class User {
constructor(name) {
this.name = name;
}
sayHi() {
alert(this.name);
}
}
let user = new User("John");
user.sayHi();
此時 User.prototype 包括
constructor
和sayHi
兩個 methods。class expression 像一般 function 一樣,也可以寫作沒有名稱的表達式:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17let User = class {
sayHi() {
alert("Hello");
}
};
function makeClass(phrase) {
// 返回並宣告一個 class
return class {
sayHi() {
alert(phrase);
};
};
}
let User = makeClass("Hello");
new User().sayHi(); // Hello使用
extends()
以及super()
來繼承父類的參數給子類。
關鍵字 extends 是在類別宣告或是類別敘述中建立子類別的方法。
若在子類別中有建構子(constructor),要使用this
前必須先呼叫super()
函式:在子類別建構子中用關鍵字 super 來呼叫父類別的建構子。1
2
3
4
5const createPersonClass = name => class extends User {
constructor() {
super(name)
}
}內部 method 之間不用逗號區分,與一般物件不同,可以避免我們描述二者時產生混淆
Class 結構中自動開啟了嚴格模式 (Use Strict)
Class 的宣告不會被 hoisting 提升到最高作用區,與函式宣告式不同,編譯器尚未抵達和執行 class 宣告之前無法建立或存取 class。
Just like literal objects, classes may include
getters/setters
computed properties etc. Protection and Control:確保內部才能修改或訪問資料,防止洩漏。
- 使用