【发布时间】:2020-04-14 11:14:46
【问题描述】:
Java 中不能通过改变返回类型来重载方法,但是我们可以通过改变返回类型(协变返回类型)来覆盖方法。 为什么?
更具体地说,JVM 使用方法的完整签名进行查找/解析。完整签名意味着它除了参数类型之外还包括返回类型。即,一个类可以有两个或多个方法,仅在返回类型上有所不同。 javac 使用这个事实来实现协变返回类型。
那么为什么我们不能重载使用协变返回类型的方法呢?
【问题讨论】:
-
对于您关于重载的问题,我相信 Java 解释器只“看到”方法名称和参数的数量/类型,而不是返回类型。因此,只有返回类型不同的两个具有相同签名的方法看起来是一样的。对于您问题的后半部分,不能随意更改覆盖的返回类型。它要么必须匹配接口中的类型或比该类型更具体。
-
@ElliottFrisch JLS 不要求使用基于堆栈的虚拟机。 JVMS 确实如此。
-
为什么——如果Java不允许被覆盖的方法使用协变返回类型,那么这会损害继承特性,我认为这就是设计人员可能会这样想的原因。跨度>
-
@TimBiegeleisen JVM 使用方法的完整签名进行查找/解析,为什么它无法区分具有不同返回类型的两种方法。
-
我的理解可能是错误的,但是我的理解是JVM去调用一个方法时,它只能通过参数的名称和数量/类型来确定调用哪个版本。如果只是两种方法的返回类型不同,JVM 就无法确定调用哪个版本。