文章目录
前言
提示:这里可以添加本文要记录的大概内容:
例如:随着人工智能的不断发展,机器学习这门技术也越来越重要,很多人都开启了学习机器学习,本文就介绍了机器学习的基础内容。
提示:以下是本篇文章正文内容,下面案例可供参考
4.4.1 Java 多态概述
Java中的多态性(Polymorphism)是指允许不同类的对象对同一消息做出响应的能力,即同一个接口可以被不同的对象以不同的方式实现。多态性分为两种:编译时多态(静态多态)和运行时多态(动态多态)。
编译时多态(静态多态)
编译时多态主要通过方法重载(Method Overloading)和运算符重载(Operator Overloading)实现。
- 方法重载:同一个类中有多个同名方法,但参数列表不同(参数的类型、数量或顺序不同)。
- 运算符重载:允许已有的运算符拥有不同的实现,使其可以对不同类型的数据执行运算。
运行时多态(动态多态)
运行时多态主要通过以下方式实现:
- 方法重写(Method Overriding):子类重新定义父类的方法。
- 接口实现:类实现接口中的方法。
要实现运行时多态,需要满足以下条件:
- 继承:必须存在继承关系。
- 方法重写:子类必须重写父类的方法。
- 向上转型(Upcasting):子类对象需要被处理为父类类型。
代码案例
// 父类
class Animal {
public void makeSound() {
System.out.println("Some sound");
}
}
// 子类
class Dog extends Animal {
@Override
public void makeSound() {
System.out.println("Bark");
}
}
public class TestPolymorphism {
public static void main(String[] args) {
Animal myAnimal = new Animal();
Animal myDog = new Dog(); // 向上转型
myAnimal.makeSound(); // 输出: Some sound
myDog.makeSound(); // 输出: Bark
// 动态绑定: 调用实际对象类型的makeSound方法
}
}
在这个例子中,Animal
是一个父类,Dog
是继承自Animal
的子类,并重写了makeSound
方法。在TestPolymorphism
类中,myDog
对象实际上是Dog
类型,但被声明为Animal
类型。当调用myDog.makeSound()
时,Java运行时会确定对象的实际类型并调用相应的方法,这就是动态多态。
流程图
下面是描述上述代码案例的流程图:
graph TD;
A[开始] --> B[定义Animal类]
B --> C{Animal类}
C --> D[定义makeSound方法]
D --> E[输出: Some sound]
B --> F[定义Dog类]
F --> G{Dog类}
G --> H[继承自Animal]
G --> I[重写makeSound方法]
I --> J[输出: Bark]
F --> K[结束Dog类定义]
K --> L[在TestPolymorphism类中]
L --> M[创建Animal对象myAnimal]
L --> N[创建Dog对象myDog]
N --> O[向上转型为Animal类型]
M --> P[调用myAnimal.makeSound()]
P --> Q[输出: Some sound]
N --> R[调用myDog.makeSound()]
R --> S[动态绑定调用Dog的makeSound]
S --> T[输出: Bark]
T --> U[结束]
说明
- 定义Animal类:首先定义一个
Animal
类,它有一个makeSound
方法。 - 定义Dog类:然后定义一个
Dog
类,它继承自Animal
类并重写了makeSound
方法。 - 向上转型:在
TestPolymorphism
类中,创建一个Dog
对象并将其赋值给Animal
类型的对象。 - 动态绑定:调用
myDog.makeSound()
时,Java运行时会根据对象的实际类型调用Dog
的makeSound
方法。
多态性是面向对象编程的核心概念之一,它提供了极大的灵活性,允许将子类对象当作父类对象来处理,同时在运行时确定具体调用哪个类的方法。
4.4.2 Java 对象类的转换
在Java中,对象之间的转换通常涉及向上转型(Upcasting)和向下转型(Downcasting)。这两种转换是多态性的重要组成部分。
向上转型(Upcasting)
向上转型是指将子类对象赋值给父类引用。这种转换是隐式的,不需要进行任何特殊操作,因为子类对象是父类的一种“特殊”形式。
代码案例:
class Animal {
public void makeSound() {
System.out.println("Some sound");
}
}
class Dog extends Animal {
@Override
public void makeSound() {
System.out.println("Bark");
}
}
public class TestUpcasting {
public static void main(String[] args) {
Animal myAnimal = new Animal();
Animal myDog = new Dog(); // 向上转型
myAnimal.makeSound(); // 输出: Some sound
myDog.makeSound(); // 输出: Bark
}
}
在这个例子中,Dog
对象被赋值给Animal
类型的引用myDog
,这是向上转型。
向下转型(Downcasting)
向下转型是指将父类对象赋值给子类引用。这种转换是显式的,需要进行强制类型转换。
代码案例:
class Animal {
public void makeSound() {
System.out.println("Some sound");
}
}
class Dog extends Animal {
@Override
public void makeSound() {
System.out.println("Bark");
}
public void barkLoudly() {
System.out.println("Bark loudly!");
}
}
public class TestDowncasting {
public static void main(String[] args) {
Animal myAnimal = new Animal();
Dog myDog = new Dog();
Animal myBeagle = myDog; // 向上转型
Dog myBeagleDowncasted = (Dog) myBeagle; // 向下转型
myBeagleDowncasted.barkLoudly(); // 输出: Bark loudly!
}
}
在这个例子中,myBeagle
是Animal
类型的引用,指向Dog
对象。要调用Dog
类特有的barkLoudly
方法,需要将myBeagle
向下转型为Dog
类型。
注意事项
- 向下转型的安全性:在进行向下转型之前,最好先检查对象的实际类型,以避免
ClassCastException
。 - 使用
instanceof
操作符:在向下转型之前,可以使用instanceof
操作符来检查对象是否是特定类型的实例。
安全向下转型的代码案例:
if (myAnimal instanceof Dog) {
Dog myDog = (Dog) myAnimal;
myDog.barkLoudly();
} else {
System.out.println("myAnimal is not a Dog");
}
在这个例子中,我们先检查myAnimal
是否是Dog
的实例,如果是,才进行向下转型。
总结
对象之间的转换是Java多态性的一个重要方面,它允许以统一的方式处理不同类型的对象。向上转型是隐式的,而向下转型是显式的,需要确保其安全性。
4.4.3 instanceof关键字
instanceof
关键字在 Java 中用于检查一个对象是否是特定类的实例。它返回一个布尔值,表示对象是否属于指定的类型或从该类型继承。
语法
objectReference instanceof className
- objectReference:要检查的对象的引用。
- className:要检查的类的名称。
如果 objectReference
指向的对象是 className
类的实例,或者该类的子类的实例,则 instanceof
运算符返回 true
;否则返回 false
。
代码案例
class Animal {
public void makeSound() {
System.out.println("Some sound");
}
}
class Dog extends Animal {
@Override
public void makeSound() {
System.out.println("Bark");
}
public void barkLoudly() {
System.out.println("Bark loudly!");
}
}
public class TestInstanceof {
public static void main(String[] args) {
Animal myAnimal = new Animal();
Animal myDog = new Dog();
if (myDog instanceof Dog) {
System.out.println("myDog is a Dog"); // 输出: myDog is a Dog
}
if (myDog instanceof Animal) {
System.out.println("myDog is an Animal"); // 输出: myDog is an Animal
}
if (myAnimal instanceof Dog) {
System.out.println("myAnimal is a Dog");
} else {
System.out.println("myAnimal is not a Dog"); // 输出: myAnimal is not a Dog
}
try {
Dog myBeagle = (Dog) myAnimal;
myBeagle.barkLoudly();
} catch (ClassCastException e) {
System.out.println("myAnimal is not a Dog and cannot be cast to Dog");
}
}
}
流程图
下面是描述上述代码案例的流程图:
说明
- 定义Animal类:首先定义一个
Animal
类,它有一个makeSound
方法。 - 定义Dog类:然后定义一个
Dog
类,它继承自Animal
类并重写了makeSound
方法,同时定义了一个barkLoudly
方法。 - 创建对象:在
TestInstanceof
类中,创建一个Animal
对象myAnimal
和一个Dog
对象myDog
。 - 使用instanceof:
- 检查
myDog
是否为Dog
实例,输出myDog is a Dog
。 - 检查
myDog
是否为Animal
实例,输出myDog is an Animal
。 - 检查
myAnimal
是否为Dog
实例,输出myAnimal is not a Dog
。
- 检查
- 向下转型:尝试将
myAnimal
向下转型为Dog
类型,由于myAnimal
实际上不是Dog
类型,会抛出ClassCastException
并捕获异常,输出myAnimal is not a Dog and cannot be cast to Dog
。
instanceof
关键字在进行类型检查和安全向下转型时非常有用,可以避免潜在的 ClassCastException
。