你好!今天,我们会结束一系列关于 OOP 原则的课程。在这一课中,我们将讨论 Java 的多态。
多态是一种处理几种类型就好像这些类型是同一种类型的功能。此外,对象的行为将因其类型而异。让我们仔细看看这个声明。
让我们从第一部分开始:“处理几种类型就好像这些类型是同一种类型的功能”。不同类型怎么可能一样?听起来有点奇怪 :/
其实都很简单。例如,在继承的一般使用中这会出现这种情况。让我们看看它是如何工作的。
假设有一个简单的 Cat 父类,它有一个 run() 方法:
这说明了多态的主要优势:灵活性。当我们需要实现许多类型共享的一些功能时,狮子、老虎和猎豹只需变成“猫”就可以。
所有的动物都是不同的,但在某些情况下,猫就是猫,不管它是什么物种 :)下面的视频可以证实这一点。
当不想要这种“一般化”,而我们需要每个物种有不同的行为时,每种类型做它自己的事情。
由于多态,你可以为各种各样的类创建一个接口(一组方法)。这会让程序不那么复杂。
即使我们扩展程序来支持 40 种类型的猫,我们仍然会使用最简单的接口:一个用于所有 40 只猫的 run() 方法。

public class Cat {
public void run() {
System.out.println("奔跑!");
}
}
现在我们将创建三个继承 Cat 的类:Lion、Tiger 和 Cheetah。
public class Lion extends Cat {
@Override
public void run() {
System.out.println("狮子奔跑速度为 80 km/h");
}
}
public class Tiger extends Cat {
@Override
public void run() {
System.out.println("老虎奔跑速度为 60 km/h");
}
}
public class Cheetah extends Cat {
@Override
public void run() {
System.out.println("猎豹奔跑速度最高为 120 km/h");
}
}
所以我们有 3 个类。让我们模拟这样一种情况,即可以像处理同一个类一样处理这些类。
想象一下,我们的一只猫生病了,需要 Dolittle(杜立德)医生的帮助。让我们试着创建一个可以治疗狮子、老虎和猎豹的 Dolittle 类。
public class Dolittle {
public void healLion(Lion lion) {
System.out.println("狮子是健康的!");
}
public void healTiger(Tiger tiger) {
System.out.println("老虎是健康的!");
}
public void healCheetah(Cheetah cheetah) {
System.out.println("猎豹是健康的!");
}
}
看起来问题已经解决了:类已经写好了,可以开始使用了。但是如果我们想扩展程序,该怎么做呢?
我们目前只有 3 种类型:狮子、老虎和猎豹。但是世界上有 40 多种猫。想象一下,如果我们为野猫、美洲虎、缅因猫、家猫和所有其他动物增加单独的类,会发生什么。
当然,程序本身会运行,但是我们必须不断地给 Dolittle 类添加新的方法来治疗每一种类型的猫。因此,它将增长到前所未有的规模。
这就是多态性的用武之地 —“处理几种类型就好像这些类型是同一种类型的功能”。我们不需要创造无数的方法来做同样的事情 — 治一只猫。
一种方法对所有猫就足够了:
public class Dolittle {
public void healCat(Cat cat) {
System.out.println("患者是健康的!");
}
}
healCat() 方法可以接受 Lion、Tiger 和 Cheetah 对象,它们都是 Cat 的实例:
public class Main {
public static void main(String[] args) {
Dolittle dolittle = new Dolittle();
Lion simba = new Lion();
Tiger shereKhan = new Tiger();
Cheetah chester = new Cheetah();
dolittle.healCat(simba);
dolittle.healCat(shereKhan);
dolittle.healCat(chester);
}
}
控制台输出:
患者是健康的!
患者是健康的!
患者是健康的!
所以我们的 Dolittle 类处理不同的类型,就好像它们是同一个类型一样。
现在让我们解决第二部分:“此外,对象的行为将根据它们的类型而不同”。
一切都很简单。在自然界,每只猫都以不同的方式奔跑。至少以不同的速度奔跑。在我们的三种猫科动物中,猎豹跑得最快,而老虎和狮子跑得较慢。换句话说,他们的行为是不同的。
多态不仅仅是把不同的类型当作一个类型来使用。它还让我们记住各种类型的不同之处,保留其各自特有的行为。
下面的例子说明了这一点。假设我们的猫在成功康复后,决定享受一下跑步的乐趣。我们将把它添加到 Dolittle 类中:
public class Dolittle {
public void healCat(Cat cat) {
System.out.println("患者是健康的!");
cat.run();
}
}
尝试运行相同的代码来治疗三种动物:
public static void main(String[] args) {
Dolittle dolittle = new Dolittle();
Lion simba = new Lion();
Tiger shereKhan = new Tiger();
Cheetah chester = new Cheetah();
dolittle.healCat(simba);
dolittle.healCat(shereKhan);
dolittle.healCat(chester);
}
结果是这样的:
患者是健康的!
狮子奔跑速度为 80 km/h。
患者是健康的!
老虎奔跑速度为 60 km/h。
患者是健康的!
猎豹奔跑速度最高为 120 km/h
这里我们清楚地看到,对象的特定行为被保留了下来,即使我们在将它们“一般化”到 Cat 之后,将所有三种动物都传递给了该方法。由于使用多态,Java 清楚地记得这不是简单的三只猫。它们是狮子、老虎和猎豹,奔跑的方式各不相同。

GO TO FULL VERSION