SOLID之LSP

简介: 里氏代换原则 LSP,Liskov Substitution Principle子类型必须能够替换掉它们的基类型若对每个类型S的对象O1,都存在一个类型T的对象O2,使得在所有针对T编写的程序P中,用O1替换O2后,程序P行为功能不变,则S是T的子类型LSP是继承关系设计基本原则,也是使OCP成为可能的主要原则之一。正是子类型的可替换性才使得使用基类类型的模块在无需修改的情况下就可以扩展,对于LSP的违反常常会导致以明显违反OCP的方式使用运行时类型辨别(RTTI),这种方式常常是使用一个显式的if语句或才if/else链去确定一个对象的类型

里氏代换原则 LSP,Liskov Substitution Principle

子类型必须能够替换掉它们的基类型

若对每个类型S的对象O1,都存在一个类型T的对象O2,使得在所有针对T编写的程序P中,用O1替换O2后,程序P行为功能不变,则S是T的子类型

LSP是继承关系设计基本原则,也是使OCP成为可能的主要原则之一。正是子类型的可替换性才使得使用基类类型的模块在无需修改的情况下就可以扩展,对于LSP的违反常常会导致以明显违反OCP的方式使用运行时类型辨别(RTTI),这种方式常常是使用一个显式的if语句或才if/else链去确定一个对象的类型

假设一个函数f,它的参数为指向某个基类B的指针或者引用。同样假设B的某个派生类D,如果把D对象作为B类型传递给f,会导致f出现错误的行为。那么D就违反了LSP。显然,D对于f来说是脆弱的。

f的编写者会想去对D进行一些测试,以便于在把D的对象传递给f时,可以使f具有正确的行为。这个测试违反了OCP,因为此时f对于B的所有派生类都不再是封闭的

IS-A

“IS-A”是严格的分类学意义上的定义,意思是一个类是另一个类的“一种”

我们经常说继承是IS-A关系,也就是如果一个新类型的对象被认为和一个已有类的对象之间满足IS-A关系,那么这个新对象的类应该从这个已用对象的类派生

从一般意义上讲,一个正方形就是一个矩形。因此,把Sequare类视为从Rectangle类派生是合乎逻辑的

void f(Rectangle r) {
    r.setWidth(5);
    r.setHeight(4);
    assert(r.Area() == 20)
}

此时,如果传入的是Sequare对象,那这个函数f不能正确处理,也就是Squauare不能替换Rectangle,也就违反了LSP,意味着LSP与通常的数学法则和生活常识有不可混淆的区别

在OOD中IS-A关系是就行为方式而言,而不是属性,这也就是面向接口编程;派生类的行为方式和输出不能违反基类已经确立的任何限制。基类的用户不应该被派生类的输出扰乱

简单判断就是“可替换性”,子类是否能替换父类并保持原有行为不变

LSP与架构

LSP从诞生开始,也就差不多这些内容,主要是指导如何使用继承关系的一种方法。随着时间推移,在更宏观上,LSP逐渐演变成了一种更广泛的、指导接口与其实现方式的设计原则

可以是java风格的接口,具有多个实现类:甚至可以是几个服务响应同一个rest接口,用户都依赖于一种接口,并且都期待实现该接口的类之间能具有可替换性

一旦违背了可替换性,该系统架构就不得不为此增添大量复杂的应对机制

目录
相关文章
|
程序员 微服务
SOLID之SRP
单一职责原则 SRP,single responsibility principle SRP是所有原则中最简单的之一,也是最难正确运用的之一,也是我们日常中最常用的一个 不管是编码,重构,甚至当下流行的微服务中 在很多团队的规范中,都会听到一条编码规范:一个方法不要超过x行代码 作为一群自命不凡的程序员,为什么在规范中却有如此一条格调不对称规范 主要问题就在于思维对SRP的缺失
145 0
|
消息中间件 架构师 前端开发
SOLID之DIP
依赖反转原则 DIP, Dependency inversion principle 1. 高层模块不应该依赖于低层模块。二者都应该依赖于抽象 2. 抽象不应该依赖于细节。细节应该依赖于抽象
140 0
SOLID之DIP
|
6月前
|
关系型数据库 测试技术
|
5月前
|
关系型数据库 开发者
|
关系型数据库 微服务
SOLID之OCP
开闭原则 OCP Open-Closed Principle 设计良好的计算机软件应该易于扩展,同时抗拒修改 换句话说,一个良好的计算机系统应该在不需要修改的前提下就可以轻易被扩展 遵循开闭原则设计出的模块具有两个特征: 1. “对于扩展是开放的”,当应用的需求改变时,我们可以对模块进行扩展,使其具有满足那些改变的新行为 2. “对于更改是封装的”,对模块进行扩展时,不必改动原有的代码
171 0
|
设计模式 架构师 Java
SOLID总结
之前已经把SOLID的每人原则都阐述过一遍,此篇主要是从全局角度复述一下SOLID,对于细节概念再做少许补充 SOLID原则的历史已经很悠久,早在20世纪80年代末期,都已经开始逐渐成型了 通常来讲,想构建一个好的软件系统,应该从写整洁的代码开始做起。毕竟如果建筑的砖头质量不佳,那么架构所能起到的作用也会很有限。反之亦然,如果建筑的架构设计不佳,那么其所用砖头质量再好也没用
365 0
SOLID总结
|
4月前
|
Java 关系型数据库
SOLID设计原则:接口隔离原则
本文探讨接口隔离原则(ISP),它是SOLID原则之一,强调不应强迫客户依赖不使用的方法。通过将接口拆分为多个具体接口,可以避免不必要的依赖,提高系统灵活性。接口隔离原则不同于单一职责原则,前者关注接口设计,后者关注类的职责划分。合理应用ISP可以提升代码质量,但在实践中需注意适度细化,避免过度设计。
61 6
|
设计模式 搜索推荐 安全
【Java设计模式 经典设计原则】三 SOLID-LSP里式替换原则
【Java设计模式 经典设计原则】三 SOLID-LSP里式替换原则
162 0

热门文章

最新文章