面向对象的三大特性之多态

今天给大家总结介绍一下面向对象的三大特性之一的多态。



多态:

概念:同样的方法,在使用不同的对象调用时,表示出不同的行为称之为多态(Java中的多态实现依赖于继承和方法重写)。

若我们理解不清楚,可以通过下面这个例子帮助记忆:
在这里插入图片描述

打印机为父类,它有彩色打印机和黑白打印机两个子类,使用彩色打印机对象调用print方法打印出来的是彩色图片,使用黑白打印机对象调用print方法打印出来的是黑白照片。简言之:多态性就是同一件事情(行为/方法),发生在不同的对象身上,表现出不同的结果。


1.多态的向上转型

向上转型发生的位置

下面的例子以Animal为父类、Dog、Cat继承Animal为子类代码如下:

package Java_3;

//父类
public class Animal {
    String name;
    int age;
    
    public Animal(String  name, int age) {
        this.name = name;
        this.age = age;
    }
    
    public void eat() {
        System.out.println(this.name + "在吃东西");
    }
}

//子类dog
class Dog extends Animal {
    public Dog(String name, int age) {
        super(name, age);
    }
    
    public void eat() {
        System.out.println(this.name+"吃狗粮");
    }
}

//子类cat
class Cat extends Animal {
    public Cat(String name, int age) {
        super(name, age);
    }
    
    public void eat() {
        System.out.println(this.name+"吃猫粮");
    }
}

a.直接赋值:

父类名称 父类引用 = new 子类实例();
Animal animal = new Dog();

b.方法传参:

    public static void main(String[] args) {

        Dog dog=new Dog("哈巴狗",6);
        Cat cat=new Cat("加菲猫",5);
        fun(dog);
        fun(cat);
    }

    public static void fun(Animal animal){
        animal.eat();
    }

形参为父类引用,根据传入的子类对象的不同,表现出来的eat方法就不同。

c.方法的返回值:

下面的方法虽然它要求返回的是一个Animal对象,但我们可以以它的子类为返回结果。

    public static Animal buyAnimal(String name) {
        if (name.equals("狗")) {
            return new Dog("狗", 1);
        } else if (name.equals("猫")) {
            return new Cat("猫", 1);
        } else {
            return null;
        }
    }
向上转型的好处

a.参数统一化:

假设现在要求实现一个方法,可以接收所有的Animal以及其子类的对象,调用eat方法。假设没有向上转型,只能当前类型的引用指向当前类型,那么有多少个子类我们就需要实现多少个eat方法;若有了向上转型,则只需要在方法形参规定父类的引用,所有该类的子类对象都能使用父类引用来接收,这时只需要写一个方法就行了。

b.方便子类进行扩展:

假设我现在要调用每个子类的方法:

不使用向上转型:

如果我增加了一个子类,则我需要重新new一个子类,在animal数组里加上该子类的对于字符串,在增强for循环里面需要重新再加上一个if else语句。

    public static void main(String[] args) {

        Dog dog = new Dog("哈巴狗", 6);
        Cat cat = new Cat("加菲猫",2);
        String[] animal={"Dog"};
        for(String str :animal){
            if(str.equals("Dog")){
                dog.eat();
            }
            else if(str.equals("Cat")){
                cat.eat();
            }
    }
}

使用向上转型:

如果我增加了一个子类,我只需要在animal数组里面再new一个就行了。

    public static void main(String[] args) {
        
        Animal[] animal={new Dog("哈巴狗",1),new Cat("加菲猫",1)};
        for(Animal a :animal){
            a.eat();
        }
    }
}

2.多态的向下转型

Aniaml animal = new Dog();
animal这个引用只能访问父类中有的属性和方法
若此时要访问子类Dog中独有的属性和方法,就需要发生向下转型。

向下转型的实现操作:

        Animal animal = new Dog("哈巴狗", 6);
        //使用instanceof关键字可以判断当前animal的引用是否指向Dog类实例
        if (animal instanceof Dog) {
            Dog dog = (Dog) animal;
        }

向下转型注意事项:

1.要想发生向下转型,必须首先先进行向上转型。
2.类型强转有风险,不能将毫无关系的两个类之间进行强转。

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

木木是木木

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值