面向对象软件设计的“开—闭”原则
1.什么是开闭原则
“开—闭”原则是指软件实体应当对扩展性开放,对修改关闭。即软件实体应该在不修改的前提下扩展,这个原则实际上为软件设计指明了目标。我们知道软件设计应当充分考虑软件的可维护性,即需求发生变化的时候软件结构能够灵活地适应这种变化。就评价软件的可维护性而言,“开—闭”原则提供了一个依据。实际上,设计模式的应用就是使软件的结构在某种程度上满足“开—闭”原则。
2.“开—闭”原则的实现
“开—闭”原则为设计提供了目标,但却没有明确给出实现的手段,下面说明在面向对象的设计中实现“开—闭”原则的方法。
(1)面向接口的编程
面向接口的编程的优势如下:
a.降低程序各部分之间的耦合性,使程序模块互换成为可能。这样客户无需知道自己使用的对象的类型,只要对象有客户所期望的接口即可。并且客户也不需要知道对象是如何实现的,只要知道定义接口的抽象类。
b.使软件各部分便于单元测试,通过编制与接口一致的模拟类(Mock),可以很容易地实现软件各部分的单元测试。从而提高软件的可靠性,降低错误率。
c.已于实现软件的模块的呼唤,软件升级时可以只部署发生变化的部分,而不会影响其它部分。
对于设计模式来说,创建型模式的产生是面向接口编程的必然结果,面向接口编程要求使用对象的客户不了解对象的具体类型,客户只能通过一个负责实例化对象的对象——我们称之为“工厂”——来实例化对象,而工厂对象在应用初始化时集中进行实例化或者在集中的模块中进行。
3.封装变化
程序中任何可能发生变化的部分都可以封装为对象,包括命令、事件、属性、算法和状态等。封装变化是实现“开—闭”原则的重要手段,也是在设计中发现对象的重要途径。因此在分析需求时,一定要注意什么是不变的,什么是可能发生变化的,以及这些可能的变化会对封装带来的影响。
例如,如果对象的行为基本不变,那么这些行为可以作为对象的方法;否则就要考虑是否抽象和封装这些行为。再如,状态可以用状态参数来表示,例如温度和压力等。可以将状态参数作为独立的属性,但如果状态参数之间相互关联,则有必要进行抽象。
总之,封装可能发生变化的部分,将可能的变化作为对象。在面向对象设计中,对象不仅是指现实中存在的事物或者可视的事物,任何可能变化的部分都是侯选对象。
4.采用组合替代继承
继承是面向对象系统的特点之一,没有继承,很多面向对象的设计就无从谈起。在设计模式中,没有哪个模式不涉及到继承。采用组合替代继承并不适合任何情况,实际上,如果没有继承,很多组合根本无法实现,涉及到基础结构的继承无法替换。
组合和继承针对模块中的复用而言,当功能需要扩展时,采用继承实现复用比较简单直观。只要派生一个类,在这个类中增加新的特性,即可实现对现有类复用。然而类继承在编译时定义,无法在运行时改变 。并且继承对子类暴露了父类的实现细节,从而破坏了封装性,使子类与父类耦合性非常强。一旦父类发生变化,必然导致子类也发生变化。如果继承下来的实现不能解决新问题,则需要修改父类,这种依赖性限制了灵活性。
如果我们希望通过增加子类来扩展功能,可能会出现如图所示的情况。
如果不修改类而仅仅依靠增加子类扩展,尽管似乎满足“开—闭”原则,但结果变得非常可笑。替换这个方案的一种方法是采用对象组合,将人的行为抽象为类,如图所示。
通过与行为对象的组合,可以扩展“人”的行为。通过增加新的行为类来实现扩展,类层次并没有增加。
对象组合在运行时通过获得对其他对象的引用来实现,组合要求对象遵守彼此的接口约定。只要符合这个约定,一个对象可以在运行时动态地玮不同的对象组合,从而实现复用。在设计时,每一部分只要关注接口约定即可,不必考虑具体的实现。因此对象组合有最小的耦合性并且更灵活,在设计模式中大量地采用了对象组合。
再次强调,继承是面向对象的基石之一。采用组合代替继承者是在需要复用的前提下,并不是所有的继承都可以用组合替代。不仅如此,没有继承,组合也无从谈起。在上面的例子中,行为的扩展仍然需要增加行为子类。
面向对象软件设计的“开—闭”原则相关推荐
- 一周技术学习笔记(第67期)-CPU的设计跟开闭原则有关系吗
你能想到CPU的设计是开闭原则的设计吗 说CPU的设计很符合软件设计的开闭原则,估计一般的同学肯定不会这样意识到.其实我也一样不太可能把它们能够想在一起,并将它们关联起来. 可确实就这样发生了.实际上 ...
- Java面向对象之开闭原则
开闭原则是面向对象的可复用设计的第一块基石,它是最重要的面向对象设计原则.开闭原则由Bertrand Meyer于1988年提出,其定义如下: 开闭原则(Open-Closed Principle, ...
- 设计模式---开闭原则
开闭原则是面向对象的可复用设计的第一块基石,它是最重要的面向对象设计原则.开闭原则由Bertrand Meyer于1988年提出,其定义如下: 开闭原则(Open-Closed Principle, ...
- 6大设计原则之开闭原则
开闭原则的定义 开闭原则的定义: 一个软件实体,如类.模块和函数应该对扩展开放,对修改关闭.即一个软件实体应该通过扩展来实现变化,而不是通过修改已有的代码来实现变化. 软件实体包括一下部分 项目或软件 ...
- 六大设计模式原则-开闭原则
一.开闭原则定义 开闭原则是面向对象的可复用设计的第一块基石,是最重要的面向对象设计原则.定义如下: 开闭原则(Open-Closed Principle, OCP):一个软件实体应当对扩展开放,对修 ...
- 面向对象软件设计原则【JAVA】(开闭原则、里氏代换、依赖倒转、接口隔离、迪米特法则、合成复用原则)
软件设计原则[JAVA](开闭原则.里氏代换.依赖倒转.接口隔离.迪米特法则.合成复用原则) 1.开闭原则 2.里氏代换原则 3.依赖倒转原则 4.接口隔离原则 5.迪米特法则 6.合成复用原则 1. ...
- 【设计模式】软件设计七大原则 ( 开闭原则 )
文章目录 一.开闭原则简介 二.开闭原则代码示例 1.商品接口 2.普通商品类 3.折扣商品类 4.测试类 一.开闭原则简介 开闭原则 : 定义 : 一个 软件实体 , 类 / 模块 / 函数 , 对 ...
- 面向对象设计原则之开闭原则
两截门--一个被水平分割为两部分的门,这样每一部分都可以独立保持开放或封闭 开放-封闭原则(The Open-Closed Principle) 软件实体(类.模块.函数)应该是可以扩展的,但是不可以 ...
- 软件设计原则(一)开闭原则(Open-Closed Principle, OCP)
狭义理解:对扩展开发,对修改封闭 在学习设计模式之前,应该先对软件设计原则有一定的了解,设计模式在一定程度上是迎合软件设计原则而产生的,脱离了软件设计原则,设计模式是没有意义的. 开-闭原则(Open ...
最新文章
- TensorFlow全家桶的落地开花 | 2019 Google开发者日
- 为什么我们的web前端变的越来越复杂
- boost::spirit模块演示了 AST 的生成,然后将其转储为人类可读的格式
- 用python编写杨辉三角金字塔_用python实现三道简单算法题:杨辉三角,蛇形矩阵,金字塔...
- inotify-tools对文件及目录访问进行记录
- sqlserve 热备用状态更新_燃气地暖一个月费用多少钱?看完收藏备用
- 周六直播丨细致入微 – OceanBase云平台安装部署实战
- 计算机底纹不起作用,CSS - 背景颜色在IE11中不起作用(CSS - background-color not working in IE11)...
- win10+ubuntu双系统安装方案
- nodejs 从gitlab拉下来后运行爆错解决
- 一个博友的SQL问题解决过程
- factory工厂模式之工厂方法FactoryMethod
- db2数据库基础知识
- 虚拟机opnsense作为dhcp服务器,在OPNsense中,通过主机名或域名访问内部设备
- webpack性能优化
- 2018SCAU校赛题解
- php无法访问_php突然不能访问的原因
- 华为stk_Aloo计算机在哪里,华为STK-AL00是什么型号
- dedecms织梦后台登录一直提示验证码错误
- CF 678F Lena and Queries
热门文章
- bootstrap源码里的function加上了+号
- 设计模式C#实现(十五)——命令模式
- rac安装grid报INS-41112错误
- servlet设置session追踪模式
- MySQL 查询重复记录
- 《从零构建前后分离web项目》:开篇 - 纵观WEB历史演变
- unity3d EasyTouch滑动屏幕移动相机观看场景
- Android之利用JSBridge库实现Html,JavaScript与Android的所有交互
- css中display设置为table、table-row、table-cell后的作用及其注意点
- 自定义grains_module pillar