在 TypeScript 中,类(Classes)是构建对象的蓝图。类可以包含属性(成员变量)、构造函数和方法。TypeScript 的类基于 ECMAScript 6 标准,并添加了一些额外的功能,使其更加强大和灵活。
定义类
一个基本的类定义如下:
class Greeter {
greeting: string;
constructor(message: string) {
this.greeting = message;
}
greet() {
return `Hello, ${this.greeting}`;
}
}
let greeter = new Greeter("world");
console.log(greeter.greet()); // "Hello, world"
继承
TypeScript 支持类的继承,这使得可以在一个类的基础上构建另一个类。使用 extends 关键字来实现继承。
class Animal {
move(distance: number = 0) {
console.log(`Animal moved ${distance} meters.`);
}
}
class Dog extends Animal {
bark() {
console.log("Woof! Woof!");
}
}
const dog = new Dog();
dog.bark(); // "Woof! Woof!"
dog.move(10); // "Animal moved 10 meters."
公共(public)、私有(private)和受保护的(protected)修饰符
TypeScript 提供了三种访问修饰符来控制类成员的可见性:
public: 默认情况下,所有的类成员都是公有的。private: 私有成员只能在声明它们的类中访问。protected: 受保护的成员可以在声明它们的类及其子类中访问。
class Animal {
public name: string;
private age: number;
protected type: string;
constructor(name: string, age: number, type: string) {
this.name = name;
this.age = age;
this.type = type;
}
getAge() {
return this.age;
}
}
class Dog extends Animal {
constructor(name: string, age: number) {
super(name, age, "Dog");
}
getType() {
return this.type;
}
}
let dog = new Dog("Buddy", 3);
console.log(dog.name); // "Buddy"
// console.log(dog.age); // Error: Property 'age' is private and only accessible within class 'Animal'.
console.log(dog.getAge()); // 3
console.log(dog.getType()); // "Dog"
readonly 修饰符
readonly 修饰符用于将属性设置为只读。一旦赋值后就不能再修改。
class Octopus {
readonly name: string;
readonly numberOfLegs: number = 8;
constructor(name: string) {
this.name = name;
}
}
let octopus = new Octopus("Octo");
// octopus.name = "NewName"; // Error: Cannot assign to 'name' because it is a read-only property.
console.log(octopus.name); // "Octo"
存取器(Getters 和 Setters)
TypeScript 允许你通过 get 和 set 关键字来定义存取器,以控制对某个属性的访问。
class Employee {
private _fullName: string;
get fullName(): string {
return this._fullName;
}
set fullName(newName: string) {
this._fullName = newName;
}
}
let employee = new Employee();
employee.fullName = "John Doe";
console.log(employee.fullName); // "John Doe"
静态属性和方法
静态成员存在于类本身而不是类的实例上。使用 static 关键字来定义静态成员。
class Grid {
static origin = { x: 0, y: 0 };
calculateDistanceFromOrigin(point: { x: number; y: number }): number {
let xDist = point.x - Grid.origin.x;
let yDist = point.y - Grid.origin.y;
return Math.sqrt(xDist * xDist + yDist * yDist);
}
}
let grid = new Grid();
console.log(Grid.origin); // { x: 0, y: 0 }
抽象类
抽象类作为其他派生类的基类使用。它们不能直接被实例化。使用 abstract 关键字定义抽象类和抽象方法。
abstract class Department {
constructor(public name: string) {}
printName(): void {
console.log("Department name: " + this.name);
}
abstract printMeeting(): void; // 必须在派生类中实现
}
class AccountingDepartment extends Department {
constructor() {
super("Accounting and Auditing"); // 派生类必须调用基类的构造函数
}
printMeeting(): void {
console.log("The Accounting Department meets each Monday at 10am.");
}
generateReports(): void {
console.log("Generating accounting reports...");
}
}
let department: Department;
// department = new Department(); // Error: Cannot create an instance of an abstract class
department = new AccountingDepartment();
department.printName(); // "Department name: Accounting and Auditing"
department.printMeeting(); // "The Accounting Department meets each Monday at 10am."
// department.generateReports(); // Error: Method doesn't exist on declared abstract class
通过这些特性,TypeScript 的类系统提供了强大的面向对象编程支持,使得开发者能够创建结构良好、可扩展和可维护的代码。