📜  Java中的协变返回类型

📅  最后修改于: 2020-03-20 01:03:57             🧑  作者: Mango

在JDK 5.0之前,无法通过更改返回类型来覆盖(重写)方法。当我们重写父类方法时,子类中重写方法的名称、参数类型和返回类型必须与父类方法完全相同。重写方法相对于返回类型是不变的

协变量返回类型

从Java 5.0开始,子类中的重写方法可能具有不同的返回类型,但是子类的返回类型应该是父类的返回类型的类型。重写方法相对于返回类型成为变体协变量返回类型基于Liskov替换原理
下面是一个简单的示例,用于了解带有方法重写的协变量返回类型。

// Java展示子类的返回类型应该是父类的返回类型的类型

// 声明两个类
class A {}
class B extends A {}
class Base
{
    A fun()
    {
        System.out.println("基类 fun()");
        return new A();
    }
}
class Derived extends Base
{
    B fun()
    {
        System.out.println("子类 fun()");
        return new B();
    }
}
public class Main
{
    public static void main(String args[])
    {
       Base base = new Base();
       base.fun();
       Derived derived = new Derived();
       derived.fun();
    }
}

输出:

基类 fun()
子类 fun()

注意:如果我们交换基类和子类的返回类型,则以上程序将无法工作。
优点:

  • 它有助于避免混淆类层次结构中存在的类型强制转换,从而使代码可读、可用和可维护。
  • 重写方法时,我们可以自由选择更具体的返回类型。
  • 这样可以防止运行时报错ClassCastExceptions。