微波EDA网,见证研发工程师的成长!
首页 > 硬件设计 > 硬件工程师文库 > 程序设计技术之开闭原则(OCP)

程序设计技术之开闭原则(OCP)

时间:08-14 来源:ZLG致远电子 点击:

周立功教授数年之心血之作《程序设计与数据结构》以及《面向AMetal框架与接口的编程(上)》,书本内容公开后,在电子行业掀起一片学习热潮。经周立功教授授权,本公众号特对《程序设计与数据结构》一书内容进行连载,愿共勉之。

第二章为程序设计技术,本文为2.4.3 开闭原则(OCP)。

>>> 2.4.3 开闭原则(OCP)

开闭原则(Open-Closed Princple,OCP)就是敏捷软件开发的基本原则之一,一个模块应该"对扩展开放,而对修改关闭。"比如,一个USB端口可以扩展,但不需要做任何修改就可以接受一个新的设备,因此,对于USB应用设备来说,一台有USB端口的计算机是扩展开放而对修改关闭的。当设计遵循OCP原则时,它可以通过增加新的代码来进行扩展,而不是修改已有的代码。比如,即使某个模块的内部实现改变了,但对外的接口也不能变,其目的是隔离变化。OCP通常要求我们对软件进行抽象,因为只有具有共性的抽象的接口,才会有具体的实现的可能性。接口放在哪里呢?应该放在用户端,而不是实现的一方。

假设只允许将0~9之内的value值push到栈中,即min=0,max=9。根据OCP原则,需要编写一个调用push()功能的函数pushWithRangeCheck()。将其共性——范围值的合法性判断包含在函数体内,而可变的value值、min和max通过形参应对。其函数原型为:

如果value值非法,则返回false;如果value值合法,则调用push()。此时,如果栈不满,则返回true,否则返回false,详见程序清单 2.36。

程序清单 2.36 范围值校验器范例程序(1)

由此可见,如果正确地应用OCP,那么以后再进行同样的改动时,则只需要添加新的代码,而不必改动已经正常运行的代码。如果仅需1-2种校验器,则上述方法非常简单明了。当需要组合多种校验器一起使用时,则上述方法传递的参数太多,而且每次push时,都要传递允许的范围参数。如果将min和max分离出来成为一个Range类型结构体,即可避免以上问题:

根据OCP开闭原则,需要再编写一个扩展push功能的pushWithRangeCheck(),范围值校验器范例程序详见程序清单 2.37。

程序清单 2.37范围值校验器范例程序(2)

如果再添加一个奇偶校验器,则需要判断push到栈中的数据是否为偶数,创建与之相应的OddEven类型结构体如下:

根据OCP开闭原则,还需要再编写一个扩展push功能的pushWithOddEvenCheck()。即:

为了避免用户直接操作成员,则需要定义相应的校验接口函数。即:

由于范围值校验函数和偶数校验函数都有一个指向当前对象的指针,因此可以将特殊的Range *pRange和OddEven *pOddEven泛化为void *pData。即:

无论是范围值校验还是偶数校验,其共性是对输入参数进行校验,因此可以共用一个函数指针。其函数原型如下:

为了便于阅读,如程序清单 2.38所示展示了通用校验器的接口。

程序清单 2.38 通用校验器的接口(validator.h)

尽管无法预知将要支持什么校验器,但调用者知道,因此可以将范围值校验器和奇偶校验器功能分离出来成为单独的函数,编写一个通用的pushWithValidate()函数,通过函数指针调用相应的校验函数,且不用在意具体校验器内部的实现,使用validator.h接口的通用校验器范例程序详见程序清单 2.39。

程序清单 2.39通用校验器范例程序

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top