论重写和里式替换原则(LSP)

本文深入浅出地解析了JAVA中重写的基本原则,包括重写的定义与里式替换原则,并详细阐述了“两同两小一大”的概念及其实质。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

对于重写的原则,很多人总是巴拉巴拉一大堆两同两小一大,记不住不说,还不明白为啥,搞得花里胡哨。

其实万事万物的结果自然有其原理,JAVA作为一门编程语言,其更是有严格的语言规范和简洁性要求。

那为啥重写看起来好特么花里胡哨啊,其实说到底就是一个话,重写的定义+里式替换原则

 

重写的定义:

  1. 父子之间
  2. 同一个方法

里式替换原则:

  1. 子类能顶替父类的位置而不会出任何问题
  2. 反之不行

由这两条我们再来看下所谓的两同两小和一大

两同说的是方法名相同,参数类型相同,其实说白了就是说两个方法相同的基本定义。

两小一大是子类的异常小于父类,子类的返回值类型小于父类,子类访问权限大于父类,其核心你就会发现是从里式推出来的。

异常:

如果子类的异常大于父类,就可能会出现捕获的问题,我try-catch的是一个I/O错误,你却抛出来一个文件类型错误,这样就GAME OVER了。

返回值:

返回值其实道理是一样的,我要的是一个String类型,,如果子类进行了类型扩充到Object,你给我传了一个char类型,同样没得玩了。

访问权限:

对于访问权限则相反了,因为如果父类是public,大家开开心心的访问,突然有点子类顶上去,大家突然发现他家不开门了,是private,那问题就大了,大家都没法工作了。

 

### 方法重写的考量 在面向对象编程中,尽管里氏替换原则提供了重要的指导方针来维护继承层次结构中的行为一致性[^2],但在实际开发过程中有时会出现违反该原则但仍需进行方法重写的情况。 #### 实际需求驱动下的权衡 有时候业务逻辑的需求变化迫使开发者调整子类的行为。例如,在特定应用场景下,可能需要增强或修改原有功能以适应新的业务场景。这种情况下,虽然形上看似违背了LSP,但从实用角度出发却是合理的解决方案之一。 ```java class PaymentMethod { public boolean processPayment(double amount) { System.out.println("Processing payment..."); return true; } } class CreditCardPayment extends PaymentMethod { @Override public boolean processPayment(double amount) throws InsufficientFundsException { if (amount > availableCredit()) throw new InsufficientFundsException(); System.out.println("Processing credit card payment with check."); return super.processPayment(amount); } private double availableCredit() { // Logic to determine available credit. return 1000.0; } } ``` 上述例子展示了支付处理流程的变化。`CreditCardPayment` 类通过抛出异常的方增加了对余额不足情况的检查机制,这实际上改变了 `processPayment()` 的契约——引入了一个额外的前提条件。然而,这样的设计变更能够更好地满足现实世界的应用需求。 #### 设计模的影响 另外一些时候,为了遵循某种设计模的要求也可能导致表面上看起来像是违反了LSP的操作。比如模板方法模允许子类定义算法框架内的具体步骤而不必完全遵照父类设定好的规则执行每一个细节动作;此时即便存在一定程度上的差异也属于合理的设计选择范围之内[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值