类设计的原则
1、什么时候需要类?
当我们需要对自己关注的单一概念(属性+操作)进行抽象。
比如我们想把木头、锁、钉子聚合成一个新的单一概念,这样我们可以只关心新概念的操作(开、关),而不必再去关注原来子概念的操作(木头怎么运动、钉子怎么运动等等)。这时候我们就需要类。
2、审慎添加新class
- 如何被创建,被析构
- 复制行为如何
- 有什么默认行为是需要被禁止的
- 和其他类之间关系如何(设计模式的领域)
- 支持怎么样的类型转换
- 一般性如何(模板编程)
3、合理运用几种类间关联关系
- public继承是 is-a 关系
- 聚合是 has-a 或者 通过a去实现
- private继承也是通过a实现,只有当需要操作protected成员时,才用它代替聚合
4、类接口要容易被使用,且不容易被误用
- 如果可以,使接口使用方式类似于标准类
- 通过限制输入参数类型,从而借助编译器,降低用户误用的概率。比如像func(int a, int b, int c)等,就容易被误会;换成func(A a, B b, C c)会更好。这里A,B,C是自定义封装的类,如Day/Month/Year
- 减少客户使用接口时,需要记忆的内容。比如不可以像客户使用接口时,必须记住要释放传进来的指针等。
5、降低编译依存度
核心点主要是以下两点:
- 在.h文件中,尽量少引入自定义的.h文件
- 在容易被众多.cpp引用的.h文件(核心类所在的.h)中,尽量少的有实现细节,最好只有接口。因为接口不易变,实现容易变。(这里的实现,既包括函数的过程实现,也包括类的私有成员)
所以,主要方法如下:
- 在.h文件中,对于参数形式,
6、检查类是否合适
检查类的办法是看它全部属性和操作,是不是抽象在一个概念上。
class WoodDoor { public: void open(); void close(); void shengxiu(); // 生锈,这不是抽象在木门的概念上 void pushback(Dingzi obj); // 打钉子,pushback是计算机术语,抽象概念不对 private: std::vector<Dingzi> vDingzi; Wood wood; };