定义删除的函数
在新标准下,我们可以通过拷贝构造函数和拷贝赋值运算符定义为删除函数来组织拷贝。删除的函数时这样一个函数:我们虽然声明它们,但不能以人恶化方式使用它们。在函数的参数列表后面加上=delete来指出我们希望将它删除:
struct NoCopy{
NoCopy()=default();//使用合成的默认构造函数
NoCopy(const NoCopy&)=delete;//阻止拷贝
NoCopy& operator=(const NoCopy&)=delete;//组织赋值
~NoCopy() =default;//使用合成的析构函数
//其他成员
}
析构函数不能是删除的成员
值得注意的是,我们不能删除析构函数。如果析构函数被删除,就无法销毁此类型的对象了。对于一个删除了析构函数的类型,编译器将不允许定义该类型的变量或创建该类的临时对象。而且,如果一个类有某个成员的类型删除了析构函数,我们也不能定义该类的变量或临时对象,因为如果一个成员的析构函数是删除的,则该成员无法被雄安会。而如果一个成员无法被销毁,则对象整体也就无法被销毁了。
对于删除了析构函数的类型,虽然我们不能定义这种类型的成员,但可以动态分配这种类型的对象。但是,不能释放这种对象:
struct NoDtor{
NoDtor()=defuault;
~NoDtor()=delete;
};
NoDtor nd;//错误:NoDtor()的析构函数是删除的
NoDtor *p=new NoDtor();//正确,但是我们不能delete p
delete p;//错误
合成的拷贝控制成员可能是删除的
如前所述,如果我们未定义拷贝控制成员,编译器会为我们定义合成的版本,类似的,如果一个类定义构造函数,编译器会为其合成一个默认构造函数。对某些类而言,编译器将这些合成的成员定义为删除的函数:
- 如果类的某个成员的析构函数是删除的或不可以访问的(例如:private的),则类的合成析构函数被定义为删除的。
- 如果类的某个成员的拷贝构造函数是删除的或不可访问的,则类的合成拷贝构造函数被定义为删除的。如果类的某个成员的析构函数时删除的或不可 访问的,则合成的拷贝构造函数也被定义为删除的。
- 如果来的某个拷贝赋值运算符是删除的或不可访问的,或类有一个const的或引用成员,则类的合成拷贝赋值运算符被定义为删除的。
- 如果类的某个成员的析构函数是删除的或不可访问的,或是类有一个引用成员,它没有类内初始化器,或是类有一个const成员,他没有类内初始化器且类型未显示默认构造函数,则该类的默认构造函数被定义为删除的。