java多态的多种表现形式

本文详细探讨了Java中多态的概念及其实现方式,通过具体示例解释了父类与子类之间的关系,包括实体类、抽象类和接口的多态特性。文章展示了如何通过继承、重写和类型转换来实现多态,以及在内存中如何存储和调用多态对象。

介绍

什么是 java 的多态?

多态是面向对象编程的一个重要特性,父类中的属性方法被子类继承之后,可以具有不同的数据类型和表现出不同的行为,这可以让同一方法在其父类及其各个子类中具有不同含义

很简单,打个比方,有 Father 父类和 Son 子类,父类和子类中有一个同名的方法,该方法被子类重写,现在父类的引用指向子类的对象,那么父类的引用去使用这个同名的方法时候用的就是子类的方法实现而不是父类的方法实现了

多态离不开三个要素:继承重写子类往父类转型

下面我们通过内存,调用以及多态实现来观察
我们看几个有趣的例子:

父类和子类都是实体类

// 父类-实体类
public class Father {
	public int father = 0;
    public String param = "这是父类参数";
    public void fun(){
        System.out.println("这是父类方法");
    }
}

// 子类-实体类
public class Son extends Father {
	public int son = 0;
    public String param = "这是子类参数";
    public void fun(){
        System.out.println("这是子类方法");
    }
}

// 测试
public class Test {
    @org.junit.Test
    public void test(){
        Father f = new Son();
        System.out.println(f.param);
        f.fun();
        System.out.println("测试结束");
    }
}
  • 多态实现

    下面我查看一下测试结果:
    可以观察到,同名参数没有重新赋值,但是同名方法被重写了,并且向上转型的时候成功调用了子类的方法
    在这里插入图片描述

  • 内存观察

    我们看一下父类的引用存储的数据:
    看来父类和子类的数据都能找的到,但实际上父类引用却无法调用子类数据,可以往下看
    在这里插入图片描述

  • 调用数据

    可以看到调用的都是父类的数据
    在这里插入图片描述

父类是抽象类,子类是实体类

// 父类-抽象类
public abstract class Father {
    public int father = 0;
    public String param = "这是父类参数";
    public abstract void fun();
}

// 子类-实体类
public class Son extends Father {
    public int son = 0;
    public String param = "这是子类参数";
    public void fun(){
        System.out.println("这是子类方法");
    }
}

// 测试
public class Test {
    @org.junit.Test
    public void test(){
        Father f = new Son();
        System.out.println(f.param);
        f.fun();
        System.out.println("测试结束");
    }
}
  • 多态实现

    父类是抽象类,就是说父类中所有的抽象方法,子类必须要重写
    我们看下结果:

    在这里插入图片描述

  • 内存观察

    父类的引用包含的数据如下:
    在这里插入图片描述

  • 调用数据

    父类的引用同样只能调用自己的数据:
    在这里插入图片描述

父类是接口,子类是实体类

// 父类-接口
public interface Father {
    public static final int father = 0;
    public static final String param = "这是父类参数";
    void fun();
}

// 子类-实体类
public class Son implements Father {
    public int son = 0;
    public String param = "这是子类参数";
    public void fun(){
        System.out.println("这是子类方法");
    }
}

// 测试
public class Test {
    @org.junit.Test
    public void test(){
        Father f = new Son();
        System.out.println(f.param);
        f.fun();
        System.out.println("测试结束");
    }
}
  • 多态实现

    父类中方法,子类必须都要重写
    我们来看控制台输出:

    在这里插入图片描述

  • 内存观察

    我们看下内存数据:
    发现 f 中没有几个自己的变量了?这是怎么回事?原来这些接口中的变量根本就是属于 f,也不是变量,而是常量,所以下图中没有显示,即使接口中不去写 public static final,接口中也会把这些变量自动添加上 public static final
    在这里插入图片描述

  • 调用数据

    下图也可以看见 f 中并无父类 param,因为他已经是 static 了,不属于父类成员变量的作用域了
    在这里插入图片描述

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

abcnull

您的打赏是我创作的动力之一

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

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

打赏作者

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

抵扣说明:

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

余额充值