摘要
默认构造函数(default constructor):类通过一个特殊的构造函数来控制默认初始化过程,这个函数称为默认构造函数。默认构造函数无须任何实参。
简单来说,默认构造函数就是在调用时不需要显示地传入实参的构造函数
合成的默认构造函数
如果我们的类没有显示地定义构造函数,那么编译器就会为我们隐式地定义一个默认构造函数。这个由编译器创建的构造函数又称为合成的默认构造函数(synthesized default constructor)
合成的默认构造函数只适合非常简单的类,有三个原因:
- 只有当类没有声明任何构造函数的时,编译器才会自动地生成默认构造函数。也就是说,当你定义了其他的构造函数时,除非我们再定义一个默认构造函数,否则类将没有默认构造函数。
- 对于某些类来说,合成的默认构造函数可能执行错误的操作。如果类包含有内置类型或者复合类型的成员,则只有当这些成员全都被赋予了类内的初始值时,这个类才适合于使用合成的默认构造函数。
- 有的时候编译器不能为某些类合成默认的构造函数。例如:
- 类中包含一个其他类类型的成员且这个成员的类型没有默认构造函数,那么编译器将无法初始化该成员。这种时候,我们必须自定义默认构造函数,否则该类将没有任何可用的默认构造函数。
- 我们可以使用
= default
要求编译器生成合成的版本(可以对默认构造函数和拷贝控制成员使用)。在新标准下,我们可以定义删除的函数(deleted function)——使用= delete
。删除的函数是这样一种函数:我们虽然声明了它们,但不能以任何方式来使用它们。 - 其他。
下面提供两个示例供大家理解为什么有的时候编译器不能为某些类合成默认的构造函数
示例1:
class test1{ //test1没有默认构造函数
int a;
test1(int x){ //这里声明了其他的构造函数,所以不会有合成的默认构造函数
a = x;
}
};
class test2{
test1 t1; //一个其他类类型的成员
int a;
};
int main(){
test t2; //会报很多错,其中包含:
// error: use of deleted function 'test2::test2()'
// error: no matching function for call to 'test1::test1()'
}
//本例对应情况 1
//如果给test1声明默认构造函数则编译成功
示例2:
class test1{
int a;
test1() = delete; //使用 =delete 声明
};
int main(){
test1 t1; // error: use of deleted function 'test1::test1()'
}
//对应情况 2
参考资料
[1] C++ Primer(第5版)中文版 p236