跳到主要内容

Java 多态

提示
  1. Java多态性的核心概念:Java中的多态性意味着一个实体(如方法或对象)在不同情况下可以表现出不同的行为。
  2. 实现多态的方式:Java中的多态可以通过方法重写、方法重载和操作符重载来实现。特别是在继承中,子类重写的方法可以根据对象类型表现不同的行为。
  3. 多态性的实际应用:多态允许创建更一致和灵活的代码。例如,使用同一个 render() 方法来渲染不同类型的图形,其行为会根据对象类型(如正方形或圆形)而改变。

以下图解展示了Java中多态性的一个实例:Polygon 类作为超类,具有 render() 方法,而 SquareCircle 作为子类,重写了 render() 方法以实现特定于正方形和圆形的渲染过程。

多态性是面向对象编程的一个重要概念。它简单地意味着一个实体(方法、操作符或对象)在不同场景下可以执行不同的操作。

示例:Java 多态性

class Polygon {

// 方法来渲染形状
public void render() {
System.out.println("渲染多边形...");
}
}

class Square extends Polygon {

// 渲染正方形
public void render() {
System.out.println("渲染正方形...");
}
}

class Circle extends Polygon {

// 渲染圆形
public void render() {
System.out.println("渲染圆形...");
}
}

class Main {
public static void main(String[] args) {

// 创建一个 Square 对象
Square s1 = new Square();
s1.render();

// 创建一个 Circle 对象
Circle c1 = new Circle();
c1.render();
}
}

输出

渲染正方形...
渲染圆形...

在上面的例子中,我们创建了一个超类:Polygon 和两个子类:SquareCircle。注意 render() 方法的使用。

render() 方法的主要目的是渲染形状。然而,渲染正方形的过程与渲染圆形的过程不同。

因此,render() 方法在不同的类中表现不同。或者,我们可以说 render() 是多态的。

为什么要使用多态?

多态允许我们创建一致的代码。在前面的例子中,我们也可以创建不同的方法:renderSquare()renderCircle() 分别用来渲染 SquareCircle

这将完美工作。然而,对于每个形状,我们需要创建不同的方法。这将使我们的代码不一致。

为了解决这个问题,Java 中的多态性允许我们创建一个单一的方法 render(),它将对不同的形状有不同的行为。

注意print() 方法也是多态性的一个例子。它用于打印不同类型的值,如 charintstring 等。

我们可以通过以下方式实现 Java 中的多态性:

  1. 方法重写
  2. 方法重载
  3. 操作符重载

Java 方法重写

Java 继承 中,如果超类和子类中都存在相同的方法。那么,子类中的方法将覆盖超类中的同名方法。这被称为方法重写。

在这种情况下,同一个方法在超类中执行一种操作,在子类中执行另一种操作。例如,

示例 1:使用方法重写实现多态

class Language {
public void displayInfo() {
System.out.println("通用英语语言");
}
}

class Java extends Language {
@Override
public void displayInfo() {
System.out.println("Java 编程语言");
}
}

class Main {
public static void main(String[] args) {

// 创建一个 Java 类的对象
Java j1 = new Java();
j1.displayInfo();

// 创建一个 Language 类的对象
Language l1 = new Language();
l1.displayInfo();
}
}

输出:

Java 编程语言
普通英语

在上面的例子中,我们创建了一个名为 Language 的超类和一个名为 Java 的子类。这里,方法 displayInfo()LanguageJava 中都存在。

displayInfo() 的用途是打印信息。然而,它在 LanguageJava 中打印的信息不同。

根据调用方法的对象,打印相应的信息。

displayInfo() 方法在使用 l1 对象调用时打印普通英语,在使用 j1 对象时打印 Java 编程语言

注意:调用的方法是在程序执行过程中确定的。因此,方法重写是运行时多态

2. Java 方法重载

在 Java 类中,我们可以创建具有相同名称但参数不同的方法。例如,

void func() { ... }
void func(int a) { ... }
float func(double a) { ... }
float func(int a, float b) { ... }

这被称为 Java 中的方法重载。这里,相同的方法会根据参数执行不同的操作。

示例 3:使用方法重载实现多态

class Pattern {

// 无参数的方法
public void display() {
for (int i = 0; i < 10; i++) {
System.out.print("*");
}
}

// 带单个参数的方法
public void display(char symbol) {
for (int i = 0; i < 10; i++) {
System.out.print(symbol);
}
}
}

class Main {
public static void main(String[] args) {
Pattern d1 = new Pattern();

// 调用无任何参数的方法
d1.display();
System.out.println("\n");

// 调用带单个参数的方法
d1.display('#');
}
}

输出:

**********

##########

在上面的例子中,我们创建了一个名为 Pattern 的类。该类包含一个名为 display() 的重载方法。

// 无参数的方法
display() {...}

// 带单个 char 类型参数的方法
display(char symbol) {...}

这里,display() 的主要功能是打印图案。然而,根据传递的参数,该方法执行不同的操作:

  • 如果没有传递参数,就打印 * 的图案,
  • 如果传递了单个 char 类型参数,就打印该参数的图案。

注意:调用的方法是由编译器确定的。因此,它也被称为编译时多态。

3. Java 运算符重载

Java 中的一些运算符对不同的操作数表现出不同的行为。例如,

  • + 运算符被重载以执行数字加法以及字符串连接,
  • 运算符如 &|! 被重载用于逻辑和位操作。

让我们看看如何使用运算符重载实现多态。

+ 运算符用于添加两个实体。然而,在 Java 中,+ 运算符执行两个操作。

  1. + 用于数字(整数和浮点数)时,它执行数学加法。例如,
int a = 5;
int b = 6;

// 数字相加
int sum = a + b; // 输出 = 11
  1. 当我们使用 + 运算符与字符串时,它将执行字符串连接(连接两个字符串)。例如,
String first = "Java ";
String second = "Programming";

// 字符串相加
name = first + second; // 输出 = Java Programming

这里,我们可以看到 + 运算符在 Java 中被重载以执行两个操作:加法连接

注意:在诸如 C++ 这样的语言中,我们可以定义运算符对不同

的操作数执行不同的操作。然而,Java 不支持用户定义的运算符重载。

多态变量

如果一个变量在不同条件下引用不同的值,就称为多态变量。

对象变量(实例变量)代表了 Java 中多态变量的行为。这是因为一个类的对象变量可以引用其类的对象以及其子类的对象。

示例:多态变量

class ProgrammingLanguage {
public void display() {
System.out.println("I am Programming Language.");
}
}

class Java extends ProgrammingLanguage {
@Override
public void display() {
System.out.println("I am Object-Oriented Programming Language.");
}
}

class Main {
public static void main(String[] args) {

// 声明一个对象变量
ProgrammingLanguage pl;

// 创建 ProgrammingLanguage 的对象
pl = new ProgrammingLanguage();
pl.display();

// 创建 Java 类的对象
pl = new Java();
pl.display();
}
}

输出:

I am Programming Language.
I am Object-Oriented Programming Language.

在上述示例中,我们创建了一个名为 ProgrammingLanguage 类的对象变量 pl。这里,pl 是一个多态变量。这是因为,

  • 在语句 pl = new ProgrammingLanguage() 中,pl 指向 ProgrammingLanguage 类的对象。
  • 而在语句 pl = new Java() 中,pl 指向 Java 类的对象。