条款19:设计class犹如设计type
今天我们主要讨论一下类的设计所面临的问题进行着手,主要解决一些思路上的问题和误区。
C++就像在其他OOP语言一样,当你定义一个新的class,那么也就定义了一个新的type。这意味这你的任务很重,不仅是class设计者,还是type设计者,重载函数,操作符,控制内存的分配和归还、定义对象的初始化和终结,全都在你手上,因此我们需要从类(class)的设计所面临的问题进行讨论:
1)新type的对象怎样被创建和销毁,影响到构造函数、析构函数、内存分配函数以及释放函数的设计(operator new,operator new[],operator delete,operator delete[]);
2)对象的初始化和对象的赋值应该有怎样的差别?这个答案决定了你的构造函数和赋值操作符的行为!
3)新type对象那个如果被pass by value(值传递),效率会被极大降低,但有什么好处呢?
4)什么是新的type的“合法值”?对class的成员变量而言,只有某些数据集是有效的,也就决定了你的成员函数必须进行的错误检查工作,例如昨天博客中所声明的Month、Day类的成员变量的取值范围;
5)你的新type需要配合某个继承图系吗?如果类进行继承的话,必定会受到相应的影响,例如析构函数是否需要声明为virtual;
6)新的type需要进行类型转换吗?需要声明为显示类型转换,还是隐式类型转换呢,隐式和显示类型转换分别需要什么样的声明呢?
7)对新的type而言,什么操作符和函数对此是合理的呢?决定了你需要为class声明那些函数和重载那些运算符,那些该声明为member成员函数?那些需要声明为non-member函数呢?
8)什么样的函数需要声明为private呢?防止外部直接调用;
9)那些成员变量需要声明为public、protected和private呢?
10)那些函数或者类需要声明为friend呢?
11)什么是新的type的“未声明的接口”,对效率、异常安全性以及资源调用提供什么保障呢?
12)你需要定义的一个type还是一系列types族呢?如果是types族的话需要定义为class template;
13)这个type必须定义吗?通过为已存在的type添加non-member函数或者templates可以满足要求呢,还需要定义吗?
总结:这个条款中我们主要是针对type的设计上的误区进行纠正,在定义新的type之前,请确定你已经深入思考过。