JAVA面向对象的本质之一:多态
一、什么是多态
多态是继封装、继承之后,面向对象的第三大特性。
多态是具有表现多种形态的能力的特征。更专业的说法:同一个实现接口,使用不同的实例而执行不同的操作,例如一个榨汁机,你将什么水果放进去,它就榨出什么水果,将苹果放进去,它就榨苹果汁,放草莓它就榨草莓汁,即出现的不同的形态
注:多态只是一种概念,并非具体实现方法(继承是多态的前提)
二、怎么实现多态:
1.子类到父类的转换(向上转型)
定义格式:父类类型 变量名=new 子类类型();
错误格式:子类类型 变量名=new 父类类型();[子类类型无法自动转换到父类类型,就好比double可以接收int类型的数值,但int无法接收double类型的数值一样,需要显示转换(强行转换)]---->正确格式:子类类型 变量名=(子类类型)new 父类类型();(向下转型)
以动物为案例
父类:Animal动物类
public class Animal {
public void eat(){
System.out.println("动物在吃");
}
}
子类:Cat猫类
public class Cat extends Animal {
public void eat(){
System.out.println("猫在吃鱼");
}
//抓鱼
public void catchFish(){
System.out.println("猫抓鱼");
}
}
子类:Dog狗类
public class Dog extends Animal{
public void eat(){
System.out.println("狗吃骨头");
}
public void housekeeping(){
System.out.println("狗看家");
}
}
如果测试类中
Animal animal=new Dog();
animal.eat();
那将会调用Dog类重写的eat()方法,而不是Animal类的eat()方法;
注:animal只能访问父类的eat()方法,无法调用Dog的housekeeping()方法
2.父类到子类的转换(向下转型)
问题来了,如果猫吃完鱼后想再抓几条鱼怎么办,Animal animal=new Cat();又无法调用猫特有的抓鱼方法
public void s(){
Animal animal=new Cat();
animal.eat();
Cat animal1=(Cat)new Animal();
animal1.catchFish();
}
上面提到,当向上转型发生后,将无法调用子类特有的方法。但是当需要调用子类特有的方法时,可以通过将父类再强转为子类来实现
3.使用父类作为方法形参实现多态
有个问题,如果主人要给这些宠物喂食,那就不得不分别写两个eat()方法给猫和狗喂食,如果由很多只不一样的宠物呢,这就违背了Java的面向对象的思想,以下代码可以解决问题
public class Master {
public void feed(Animal a){
a.eat();
}
}
测试类中
public static void main(String[] args) {
Dog dog=new Dog();
Master master=new Master();
master.feed(dog);
}
需要喂食什么动物就给什么对象
4.使用父类作为方法返回值类型实现多态
public class Master {
public Animal1 adopt(){
Animal1 animal=new Cat();
return animal;
}
public static void main(String[] args) {
Animal a= master.adopt();
Cat animal=(Cat) a;
animal.catchFish();
}
三、instanceof运算符
上面的Cat animal1=(Cat)new Animal();类似于C#的as(强行转换)
那么instanceo就类似于C#的is(判断类型)
语法
boolean 变量名=对象 instanceo 类或接口
问题:如果主人想猫吃完鱼就去抓鱼,狗吃完骨头就去看家,怎么实现?以猫为例
public class Master {
Animal a=new Animal();
a.eat();//猫和狗共有的方法
if(a instanceo Cat){
Cat animal=(Cat) a;
animal.catchFish();
}eles{
Dog animal1=(Dog) a;
animal.catchFish();
}
}
该运算符用来判断一个对象是否属于一个类或一个接口,返回类型为boolean类型。在强转类型转换前通过instanceo 运算符检查对象的真实类型,再进行相应的强制类型转换,这样就可以避免类型转换异常,从而提高代码的健壮性。
四、总结
使用多态的好处:
1.可替换性。多态对已存在代码具有可替换性。
2.可扩充性。多态对代码具有可扩充性。增加新的子类不影响已存在类的多态性、继承性,以及其他特性的运行和操作。实际上新加子类更容易获得多态功能。
3.接口性。多态是超类通过方法签名,向子类提供了一个共同接口,由子类来完善或者覆盖它而实现的。
4.灵活性。它在应用中体现了灵活多样的操作,提高了使用效率。
5.简化性。多态简化对应用软件的代码编写和修改过程,尤其在处理大量对象的运算和操作时,这个特点尤为突出和重要。
(本帖为纯自制内容,可能有些点没有讲到,后面会继续修改优化)