TypeScript真香系列的內容將參考中文文檔,可是文中的例子基本不會和文檔中的例子重複,對於一些地方也會深刻研究。另外,文中一些例子的結果都是在代碼沒有錯誤後編譯爲JavaScript獲得的。若是想實際看看TypeScript編譯爲JavaScript的代碼,能夠訪問TypeScript的在線編譯地址,動手操做,印象更加深入。javascript
TypeScript中的類和ES6中的類十分類似,從下面這個例子就可以看出來了:java
class Man{
name: string;
constructor(msg: string) {
this.name= msg;
}
play() {
return "Hello, " + this.name;
}
}
let man = new Man("James");
man.name; //"James"
man.play(); //"Hello, James"
複製代碼
咱們在上面聲明瞭一個Man類,類中有三個成員:分別爲name屬性,構造函數,play方法。git
TypeScript中類的繼承也和ES6中相似,派生類(子類)能夠從基類(父類)中繼承屬性和方法。github
class Man{
name: string;
constructor(msg: string) {
this.name= msg;
}
play() {
return "Hello, " + this.name;
}
}
class Player extends Man {
age: string;
constructor(name: string,age:string) {
super(name)
this.age = age;
}
showAge() {
return this.age;
}
}
let player = new Player("James","35");
player.age; //"35"
player.name; //"James"
player.play(); //"Hello, James"
複製代碼
在上面的代碼中,Man類就是咱們的基類,Player 類就是咱們的派生類。經過關鍵字extends ,咱們就能夠實現類的繼承。若派生類中包含了構造函數,則必須調用super(),它會執行基類的構造函數。typescript
在TypeScript中,成員都是默認標記爲public,能夠理解爲公開,因此咱們能夠自由的訪問程序裏面定義的成員。固然咱們也能夠顯式的標記出來:函數
class Man{
public name: string;
public constructor(msg: string) {
this.name= msg;
}
public play() {
return "Hello, " + this.name;
}
}
複製代碼
咱們能夠把類中的成員標記爲private,能夠理解爲私有的。一旦成員標記標記爲private,咱們就不能在它的類的外部訪問它。ui
class Man {
private name: string;
constructor(msg: string) {
this.name = msg;
}
}
new Man("James").name; // 錯誤: 'name' 是私有的.
複製代碼
而且在Man的派生類中也是不能訪問的:this
class Man {
private name: string;
constructor(msg: string) {
this.name = msg;
}
}
class Player extends Man {
constructor(name: string) {
super(name);
}
}
let player = new Player("James");
player.name; //錯誤, 'name' 是私有的.
複製代碼
若是想要訪問Man類中的name,那麼咱們能夠在Man類中定義一個方法show():spa
class Man {
private name: string;
constructor(msg: string) {
this.name = msg;
}
show() {
return this.name;
}
}
class Player extends Man {
constructor(name: string) {
super(name);
}
}
let player = new Player("James");
plager.show(); //"James"
複製代碼
咱們還能夠用下面這個修飾符來進行相似的操做。code
protected,可理解爲受保護的,和private類似,有一點不一樣的就是,protected成員能夠在派生類中能夠訪問:
class Man {
protected name: string;
constructor(msg: string) {
this.name = msg;
}
}
class Player extends Man {
constructor(name: string) {
super(name);
this.name = name;
}
show() {
return this.name
}
}
let man = new Man("James");
man.name; //錯誤, 'name' 是受保護的.
let player = new Player("James");
player.name; //錯誤, 'name' 是受保護的.
player.show(); // "James"
複製代碼
protected固然也能夠標記構造函數。當構造函數被protected標記後,當前類就不能被實例化了,可是能夠被派生類繼承:
class Man {
protected name: string;
protected constructor(msg: string) {
this.name = msg;
}
}
class Player extends Man {
constructor(name: string) {
super(name);
this.name = name;
}
}
let man = new Man("James"); //錯誤,Man的構造函數是受保護的
let player = new Player("James");
複製代碼
咱們能夠使用readonly將成員設置爲只讀,只讀屬性必須在聲明時或構造函數裏被初始化。
class Man {
readonly name: string;
constructor(msg: string) {
this.name = msg;
}
}
let man = new Man("James");
man.name = "wade"; //錯誤,name是隻讀屬性
複製代碼
咱們還有另外一種寫法:
class Man {
constructor(readonly name: string) {
}
}
let man = new Man("James");
複製代碼
對比上面種寫法,發現下面這種方式簡潔了許多,這是咱們使用了參數屬性。參數屬性可讓咱們方便的在一個地方定義並初始化一個成員,並且能夠經過給構造函數前面添加一個訪問限定符(public,private,protected)來進行聲明。以下所示:
//使用前
class Man {
public name:string
constructor(name: string) {
this.name = name
}
}
//使用後
class Man {
constructor(public name: string) {
}
}
複製代碼
在TypeScript中,咱們能夠利用存取器來幫助咱們有效的控制對對象成員的訪問。 首先看沒有存取器的版本:
class Man {
public name: string;
constructor(msg: string) {
this.name = msg
}
}
let man = new Man("James");
man.name = "wade";
console.log(man.name); // wade
複製代碼
而後是存取器版本:
class Man {
public _name: string;
constructor(msg: string) {
this._name = msg;
}
get myName(): string{
return this._name;
}
set myName(newName: string) {
this._name = newName;
}
}
let man = new Man("James");
console.log(man.myName); // James
man.myName = "wade";
console.log(man.myName); // wade
複製代碼
這裏有兩個地方須要注意:一是,存取器要求咱們配置時將編譯器設置爲輸出ECMAScript 5或更高的版本;二是,存取器只帶get不帶set的話,存取器會自動推斷爲readonly。
TypeScript的靜態屬性和JavaScript中的靜態屬性是相似的。咱們建立的類的靜態成員,這些屬性是在類的自己而不是在類的實例上:
class Man {
static player: string = "運動員";
show() {
return "我職業:" + Man.player
}
}
let man = new Man();
man.player; //錯誤,player是靜態成員
Man.player; // 運動員
man.show(); // 我職業:運動員
複製代碼
TypeScript中的抽象類是提供其餘派生類的基類,可是不能直接被實例化。咱們能夠用abstract關鍵字來定義抽象類和抽象類中的方法。其用法以下:
abstract class Man {
constructor(public name: string) {
}
show() {
return "個人名字:" + this.name
}
abstract play(type:string): void; //這個方法必須在派生類中實現,否則派生類就會報錯
}
class Player extends Man {
constructor(name:string) {
super(name) //派生類中的構造函數必須調用super()
}
play(type:string) {
return "個人職業是" + type;
}
go() {
return "沖沖衝";
}
}
let man: Man; //能夠建立一個對抽象類的引用
man = new Man("James"); // 錯誤,不能建立一個抽象類的實例
man = new Player("Wade"); //能夠對一個抽象子類進行進行實例化和賦值
man.go(); //錯誤,go方法在聲明的抽象類中不存在
man.play("basketball"); //"個人職業是basketballer"
複製代碼
文中有些地方可能會加入一些本身的理解,如有不許確或錯誤的地方,歡迎指出~ 祝你們新年快樂,闔家辛福! 但願前線的醫護人員健健康康,早日戰勝病毒! 但願你們都健健康康!