TypeScript 如何实现多态

你有没有过这种情况?写代码时明明定义了一个“交通工具”类,想让它不管是汽车还是自行车都能正常跑,结果写了一堆重复逻辑还总报错?其实只要用点小技巧,就能让同一段代码适配不同的情况——这就是“多态”的魔力,而TypeScript里实现它,其实比你想的简单。

先搞懂多态到底在说啥

不用记复杂定义,咱们举个生活里的例子:你买奶茶的时候,不管选珍珠、椰果还是芋圆,都可以说“加半糖”,奶茶店只会按你选的配料做,不会因为你选了不同配料就重新教你怎么加糖。放到代码里,多态就是:同一个“做奶茶”的指令,能对应不同的“配料制作方法”,不用每次都改指令本身。

TypeScript 如何实现多态

放到TypeScript里,就是让同一个函数或类方法,能处理不同类型的对象,既不用写重复代码,也不会出错。

第一种实现:子类“重写”父类方法

这是最常用的方式,就像上面的奶茶例子:父类是“基础奶茶”,子类是带不同配料的奶茶,每个子类可以根据自己的特点,修改父类的“做奶茶”方法。

举个实际的代码小例子:咱们先定义一个“交通工具”的父类,里面有个“跑”的方法,就是简单喊一句“我在跑”;然后做两个子类,汽车和自行车,分别改“跑”的内容:

`typescript

// 父类

class Vehicle {

run() {

console.log("这是交通工具在跑");

}

}

// 汽车子类

class Car extends Vehicle {

run() {

console.log("汽车在公路上跑");

}

}

// 自行车子类

class Bike extends Vehicle {

run() {

console.log("自行车在非机动车道上骑");

}

}

`

现在不管你拿汽车对象还是自行车对象,只要调用同一个run(),就能得到对应交通工具的结果——这就是多态。你看,不用写两个不同的方法,同一个指令适配了不同的情况,是不是很省事儿?

第二种实现:用接口统一“行为规范”

如果不想用类的继承,也可以用接口来实现多态。接口就像“行为说明书”,只要某个对象符合“会跑”的说明书(也就是实现了run方法),就能用同一个函数来处理。

比如咱们做个“会跑”的接口,要求任何符合这个接口的东西,都得有run方法;然后让汽车和自行车都遵守这个规范,最后写一个“让它跑起来”的函数,不管传什么,只要有run方法就可以:

`typescript

// 行为接口

interface CanRun {

run(): void;

}

// 汽车符合这个行为

class Car implements CanRun {

run() {

console.log("汽车在公路上跑");

}

}

// 自行车也符合这个行为

class Bike implements CanRun {

run() {

console.log("自行车在非机动车道上骑");

}

}

// 统一处理的函数

function startRunning(vehicle: CanRun) {

vehicle.run();

}

`

现在不管传new Car()还是new Bike()给startRunning,都能正常执行。哪怕以后加个“滑板车”,只要它实现了run方法,就能直接用这个函数,完全不用改原来的代码。

为什么要做这件事?

很多人会问,为啥非得搞多态?其实就是为了“省事儿”。如果没有多态,你要给每个交通工具都写一个单独的runCar、runBike函数,每次加新交通工具都要加新函数,代码会越来越乱。多态让你只需要写一次通用逻辑,就能适配所有符合规则的对象,不管是刚加的滑板车,还是以后新出的飞行器,都能直接用。

TypeScript的多态没有那么多复杂的规则,核心就是“统一规则,各自实现”——要么让子类改父类的方法,要么让对象遵守同一个接口,最后用同一个入口调用就行,简单又好用。

上一篇 JavaScript 如何做倒计时