有下面的两个C++代码:
class MyClass {
public:
std::string str; // std::string 有默认构造函数,可以不显式初始化
};
class AnotherClass {
public:
MyClass obj; // MyClass 有默认构造函数,可以不显式初始化
};
class MyClass {
public:
MyClass(int value) {} // 没有默认构造函数
};
class AnotherClass {
public:
MyClass obj; // 由于MyClass没有默认构造函数,所以类成员obj需要在类AnotherClass的构造函数的初始化列表中进行初始化。
AnotherClass() : obj(42) {} // 必须显式初始化
};
为什么说第1个代码中类MyClass有默认的构造函数,而第2个代码中类MyClass没有默认的构造函数?
答:
在 C++ 中,默认构造函数是指不带任何参数,或者所有参数都有默认值的构造函数。如果一个类没有定义任何构造函数,编译器会自动生成一个隐式默认构造函数。
第 1 段代码分析
class MyClass {
public:
std::string str; // std::string 有默认构造函数,可以不显式初始化
};
这里 MyClass 没有显式声明构造函数,但因为 C++ 编译器会自动提供一个默认构造函数,即:
MyClass() {} // 编译器自动生成
这样,MyClass 拥有默认构造函数,可以被默认初始化。
此外,std::string 本身有默认构造函数,所以 str 也会被正确初始化。
所以 MyClass 有默认构造函数,可以被 AnotherClass 默认初始化:
class AnotherClass {
public:
MyClass obj; // MyClass 有默认构造函数,可以不显式初始化
};
第 2 段代码分析
class MyClass {
public:
MyClass(int value) {} // 没有默认构造函数
};
在这个代码中,MyClass 显式定义了一个带参数的构造函数:
MyClass(int value);
一旦类定义了任何构造函数,编译器就不会自动提供默认构造函数。由于这里 没有提供 MyClass() 无参构造函数,因此 MyClass 没有默认构造函数。
接下来看 AnotherClass:
class AnotherClass {
public:
MyClass obj; // 由于MyClass没有默认构造函数,所以类成员obj需要在类AnotherClass的构造函数的初始化列表中进行初始化。
AnotherClass() : obj(42) {} // 必须显式初始化
};
AnotherClass的成员变量obj是MyClass类型的。- 类型为类的成员变量必须通过默认构造函数初始化,但
MyClass没有默认构造函数,所以编译器会报错:error: no default constructor exists for class 'MyClass' - 解决办法:在构造函数初始化列表中显式调用
MyClass的构造函数:AnotherClass() : obj(42) {} // 正确
总结
| 代码 | MyClass 有默认构造函数吗? | 原因 |
|---|---|---|
| 第 1 段 | ✅ 有 | 编译器自动生成默认构造函数 |
| 第 2 段 | ❌ 没有 | 自定义了带参数构造函数,编译器不会再提供默认构造函数 |
因此,在 第 1 段代码 中,MyClass 有默认构造函数,所以 AnotherClass 可以直接默认初始化。而在 第 2 段代码 中,MyClass 没有默认构造函数,必须手动提供初始化值,否则会报错。
C++中类默认构造函数的有无分析
4万+

被折叠的 条评论
为什么被折叠?



