如何在 TypeScript 中建立抽象類?


抽象簡介

我們希望讀者在實現抽象類之前,能夠熟悉抽象類及其要求。抽象意味著隱藏。它用於向用戶和某些開發人員隱藏底層程式碼實現。此外,它用於僅顯示方法的必要資訊,而不是顯示方法的整個複雜實現。

建立抽象類

我們可以使用 abstract 關鍵字來定義抽象類或方法。抽象類可以包含普通和抽象型別的方法。在抽象類中,我們需要實現功能或普通方法,並且只需要宣告抽象方法。

我們可以使用任何其他類繼承抽象類,但我們需要將抽象類中的所有抽象方法實現到繼承類中。如果我們不想在繼承類中實現抽象方法,我們需要使用 abstract 關鍵字將繼承類也設為抽象類。

此外,我們不能建立抽象類的物件,但可以建立繼承類的物件並使用抽象類方法。抽象類的限制是,我們不能使用多個抽象類實現多重繼承。

語法

使用者可以按照以下語法建立抽象類並將其繼承到其他類。

abstract class sample {
   // define variables inside the abstract class,
   // declare the abstract methods or non-abstract method inside the abstract class
   abstract demo(string): void;
}
// extend sample class and implement all abstract methods of sample to demo class
class test extends sample {
   demo(name: string): void {
      // code for the demo method
   }
}

步驟

  • 步驟 1 − 定義名為 sample 的抽象類,其中包含名為 propert1 和 property2 的屬性。

  • 步驟 2 − 此外,在 sample 類中新增建構函式以初始化 property1 和 property2 的值。

  • 步驟 3 − 在抽象類內部宣告抽象方法名稱 demo()。此外,定義抽象類的 save() 方法,這是一個非抽象方法,用於列印 property1 和 property2 的值。

  • 步驟 4 − 定義 test 類,這是一個非抽象類,繼承自 sample 類。此外,將字串型別的 property3 新增到 test 類。

  • 步驟 5 − 向 test 類新增建構函式,該建構函式接受 3 個引數,並使用前 2 個引數呼叫超類的建構函式,即 sample 類。

  • 步驟 6 − 在 test 類內部實現 sample 類的 demo() 方法,該方法列印 property3 的值。

示例 1

在下面的示例中,我們定義了包含抽象方法的抽象類。在繼承的 test 類中,我們實現了 sample 類的抽象方法。接下來,我們使用 3 個引數建立了 test 類的物件,並使用該物件呼叫了 demo() 和 save() 方法。

abstract class sample {
   // define variables inside the abstract class,
   property1: string;
   constructor(property1: string, property2: number) {
      this.property1 = property1;
   }
   // declare the abstract methods
   abstract demo(): void;
   
   // defining the non-abstract methods
   save(): void {
      console.log("The save method of the abstract class is executed.");
   }
}
// extend sample class and implement all abstract methods of sample to demo class
class test extends sample {
   property2: number;
   constructor(property1: string, property2: number) {
      super(property1);
      this.property2 = property2;
   }
   demo(): void {
      // code for the demo method
      console.log("The value of the property 3 is " + this.propert2);
   }
}
let test_obj = new test("TutorialsPont", 9999);
test_obj.demo();
test_obj.save();

在上面的示例中,我們隱藏了繼承類 test 中 save() 方法的實現。我們允許開發人員根據需要實現 demo() 方法,但隱藏其他類資訊,例如 property1、property2 和 save() 方法的實現。

現在,使用者正確理解了使用抽象類的動機以及我們如何使用它來隱藏資訊並僅顯示所需資訊。

編譯後,以上程式碼將生成以下 JavaScript 程式碼:

var __extends = (this && this.__extends) || (function () {
   var extendStatics = function (d, b) {
      extendStatics = Object.setPrototypeOf ||
      ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
      function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
      return extendStatics(d, b);
   };
   return function (d, b) {
      extendStatics(d, b);
      function __() { this.constructor = d; 
   }
   d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
})();
var sample = /** @class */ (function () {
   function sample(property1, property2) {
      this.property1 = property1;
   }
   // defining the non-abstract methods
   sample.prototype.save = function () {
      console.log("The save method of the abstract class is executed.");
   };
   return sample;
}());
// extend sample class and implement all abstract methods of sample to demo class
var test = /** @class */ (function (_super) {
   __extends(test, _super);
   function test(property1, property2) {
      var _this = _super.call(this, property1) || this;
      _this.property2 = property2;
      return _this;
   }
   test.prototype.demo = function () {
      // code for the demo method
      console.log("The value of the property 3 is " + this.propert2);
   };
   return test;
}(sample));
var test_obj = new test("TutorialsPont", 9999);
test_obj.demo();
test_obj.save();

輸出

它將產生以下輸出:

The value of the property 3 is undefined
The save method of the abstract class is executed.

示例 2

在下面的示例中,class1 是抽象類,其中包含抽象方法名稱 method1 的宣告。class2 僅包含 method2() 的定義。它擴充套件了 class1 但沒有實現名為 method1() 的抽象方法。

之後,我們定義了 class3 並透過 class2 繼承它。此外,我們在 class3 中定義了 class 內部 method1。最後,我們建立了 class3 的物件並呼叫了 method1() 和 method2()。

// define the abstract class1 containing the abstract method1
abstract class class1 {
   abstract method1(): void;
}
// Need to create class2 to abstract as we inherited class1 but doesn't defined abstract method1()
abstract class class2 extends class1 {
   method2(): void {
      console.log("Inside the method 2 of class2.");
   }
}
// defining the class3 inherited by the class2
class class3 extends class2 {
   // Implementation of the method1 of the abstract class1
   method1(): void {
      console.log(
         "Implemented the abstract method name method1 of class1 inside the class3"
      );
   }
}
// Crating the object of the class3
var object = new class3();

// Invoking the method1 of class1 which is declared in the abstract class1
object.method1();

// Invoking the method2 of class2
object.method2();

上面的示例向我們展示了,如果我們透過任何類繼承抽象類並且不想在繼承類中實現抽象方法,則需要將繼承類設為抽象類。

編譯後,以上程式碼將生成以下 JavaScript 程式碼:

var __extends = (this && this.__extends) || (function () {
   var extendStatics = function (d, b) {
      extendStatics = Object.setPrototypeOf ||
         ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
         function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
         return extendStatics(d, b);
      };
      return function (d, b) {
         extendStatics(d, b);
         function __() { this.constructor = d; }
         d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
      };
})();
// define the abstract class1 containing the abstract method1
var class1 = /** @class */ (function () {
   function class1() {
   
   }
   return class1;
}());
// Need to create class2 to abstract as we inherited class1 but doesn't defined abstract method1()
var class2 = /** @class */ (function (_super) {
   __extends(class2, _super);
   function class2() {
      return _super !== null && _super.apply(this, arguments) || this;
   }
   class2.prototype.method2 = function () {
      console.log("Inside the method 2 of class2.");
   };
   return class2;
}(class1));
// defining the class3 inherited by the class2
var class3 = /** @class */ (function (_super) {
   __extends(class3, _super);
   function class3() {
   return _super !== null && _super.apply(this, arguments) || this;
   }
   // Implementation of the method1 of the abstract class1
   class3.prototype.method1 = function () {
      console.log("Implemented the abstract method name method1 of class1 inside the class3");
   };
   return class3;
}(class2));
// Crating the object of the class3
var object = new class3();

// Invoking the method1 of class1 which is declared in the abstract class1
object.method1();

// Invoking the method2 of class2
object.method2();

輸出

它將產生以下輸出:

Implemented the abstract method name method1 of class1 inside the class3
Inside the method 2 of class2.

使用者在本教程中學習瞭如何實現抽象類。現在,使用者可以理解我們如何使用抽象類和抽象方法隱藏類的其他資訊。

此外,使用者可以使用介面進行抽象。TypeScript 中介面的所有方法都是抽象的,並且不允許非抽象方法。此外,我們可以使用介面進行多重繼承。

更新於: 2023年1月16日

1K+ 瀏覽量

啟動你的 職業生涯

透過完成課程獲得認證

開始
廣告