LSP原则与重写Override区别,协变与逆变。

LSP原则:只要父类能出现的地方,子类就可以出现,并且替换为子类也不会产生任何错误或异常。
1.子类型可以增加方法,但不可删
2.子类型需要实现抽象 类型中的所有未实现方法
3.子类型中重写的方法 必须有相同或子类型的返回值或者符合协变的参数
4.子类型中重写的 方法必须使用同样类型的参数或者符合逆变的参数。
5.子类型中重写的方 法不能抛出额外的异常 ,子类型也可以不抛出异常。异常必须满足协变。
6.Same or stronger invariants 更强的不变量
7.Same or weaker preconditions 更弱的前置条件
8.Same or stronger postconditions 更强的后置条件

重写Override
(1)重写方法必须和被重写方法具有相同的参数列表(包括顺序及个数还有类型),返回类型必须和被重写方法的返回类型相同或者是返回类型的子类型。(这个与LSP的第3条是一个意思,后文会解释协变)

(2)重写方法的访问控制修饰符不能比被重写方法更严格(比如一个在父类中声明为public的方法重写成一个protected的方法)。

(3)只有实例方法才能被重写,超类中的static和final方法不能被重写。

(4)重写方法不能抛出新的检查异常,或者是抛出比被重写方法声明的检查异常更广泛的检查异常。(这个与LSP第五条是一个意思)

(5)注意一种特殊情况:如果超类的方法版本中声明了检查异常,但重写的子类方法中没有声明,这时如果使用多态的方式进行调用,那么编译器认为你调用的是声明了异常的方法。

(6)尽管多态是在编译时确定对象的类型,但在编译时,还是根据父类的方法声明进行程序检查。因此,如果子类中定义的方法,在父类中没有定义,则会出项编译错误。

综上:LSP的第3 5条和Override的规则是一样的。但是对于第四条来讲。在Java中,如果参数列表发生了变化,是当作overload来看待的。如果你加了@Override编译器在静态检查的时候会报错的。

例如:

public class parent {
 public Number name(String string) throws IOException, NullPointerException {
  return null;
 }
}
public class child1 extends parent {
 @Override
 public Integer name(Object object) throws NullPointerException{
  return null;
 }
}

在这里插入图片描述
由例子可以看出,在子类Override时候可以少抛出异常,但是对于参数如果逆变的话,编译器会报错的。

协变:
如果A是B的子类,那么A中的类型T也是B中类型T’的子类,那么就是协变。也就是越来越具体。
在这里插入图片描述

在这里插入图片描述
逆变::如果A是B的子类,但是A中的类型T是B中类型T’的父类性,那么就是逆变。

在这里插入图片描述在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值