面向对象设计原则
单一职责原则
一个对象应该只包含单一的职责,并且该职责被完整地封装在一个类中
单一职责原则是实现高内聚、低耦合地指导方针
开闭原则
软件实体应当对扩展开放,对修改关闭
- 软件实体应尽量在不修改原有代码地情况下进行扩展
利用相对稳定地抽象层+灵活的具体层
里氏代换原则定义
所有引用基类的地方必须能透明地使用其子类的对象
- 在软件中将一个基类对象替换成它的子类对象,程序将不会产生任何错误和异常,反过来则不成立。如果一个软件实体使用的是一个子类对象的话,那么它不一定能够使用基类对象
我喜欢动物 → 我喜欢狗
依赖倒转原则
高层不应该依赖低层模块,它们都应该依赖于抽象。抽象不应该依赖于细节,细节应该依赖于抽象。
【例】组装电脑
现要组装一台电脑,需要配件cpu,硬盘,内存条。只有这些配置都有了,计算机才能正常的运行。选 择cpu有很多选择,如Intel,AMD等,硬盘可以选择希捷,西数等,内存条可以选择金士顿,海盗船 等。
上面代码可以看到已经组装了一台电脑,但是似乎组装的电脑的cpu只能是Intel的,内存条只能是金士顿的,硬盘只能是希捷的,这对用户肯定是不友好的,用户有了机箱肯定是想按照自己的喜好,选择自己喜欢的配件。
根据依赖倒转原则进行改进: 代码我们只需要修改Computer类,让Computer类依赖抽象(各个配件的接口),而不是依赖于各个 组件具体的实现类。
接口隔离原则
客户端不应该依赖那些它不需要的接口
- 当一个接口太大时,需要将它分割成一些更细小的接口
- 使用该接口的客户端仅需知道与之相关的方法即可
- 每个接口应该承担一种独立的角色
这里借用黑马程序员课程中的例子
我们需要创建一个 黑马 品牌的安全门,该安全门具有防火、防水、防盗的功能。可以将防火,防水,防 盗功能提取成一个接口,形成一套规范。类图如下:
上面的设计我们发现了它存在的问题,黑马品牌的安全门具有防盗,防水,防火的功能。现在如果我们 还需要再创建一个传智品牌的安全门,而该安全门只具有防盗、防水功能呢?很显然如果实现 SafetyDoor接口就违背了接口隔离原则,那么我们如何进行修改呢?看如下类图:
这样就实现了接口隔离原则
合成复用原则
优先使用对象组合,而不是继承来达到复用的目的
合成复用原则就是在一个新的对象里通过关联关系来使用一些已有的对象,使之成为新对象的一部分。
【例】汽车分类管理程序
汽车按“动力源”划分可分为汽油汽车、电动汽车等;按“颜色”划分可分为白色汽车、黑色汽车和红色 汽车等。如果同时考虑这两种分类,其组合就很多。类图如下:
从上面类图我们可以看到使用继承复用产生了很多子类,如果现在又有新的动力源或者新的颜色的话, 就需要再定义新的类。我们试着将继承复用改为聚合复用看一下。
迪米特法则
如果两个软件实体无须直接通信,那么就不应当发生直接的相互调用,可以通过第三方转发 该调用。其目的是降低类之间的耦合度,提高模块的相对独立性。