c++ - 构造函数“=default”和C++中编译器生成的构造函数有什么区别?
问题描述
代码示例:
class Dog
{
private:
int x;
public:
Dog()=default;
};
比。这段代码:
class Dog
{
private:
int x;
};
“=default”的构造函数(第一个代码)和编译器创建的构造函数(如第二个代码)有什么区别?
解决方案
Dog() = default;
是用户声明的构造函数(不要与用户定义的构造函数混淆)。它是一个默认的默认构造函数。通常,当类具有其他构造函数但您仍然希望编译器生成默认构造函数(或者更确切地说是“默认默认构造函数”。这是最好的 C++ 术语。注意两个“默认”如何稍微不同的意思)。
用户声明的构造函数可防止类成为聚合。来自cppreference,仅适用于 C++20:
聚合是以下类型之一:
- 数组类型
- 类类型(通常是结构或联合),具有
- 没有私有或受保护的直接非静态数据成员
- 没有用户声明或继承的构造函数
- 没有虚拟、私有或受保护的基类
- 没有虚拟成员函数
例如,考虑:
#include <iostream>
#include <type_traits>
class Dog {
int x;
public:
Dog()=default;
};
class Horse {
int x;
};
class Swan {
public:
int x;
};
class Cow {
public:
int x;
Cow() = default;
};
int main() {
std::cout << std::is_aggregate_v<Dog>;
std::cout << std::is_aggregate_v<Horse>;
std::cout << std::is_aggregate_v<Swan>;
std::cout << std::is_aggregate_v<Cow>;
}
输出
0010
前两个Dog
和Horse
类似于您的两个版本的Dog
. 它们不是聚合,因为它们有私有成员。Swan
是一个聚合,但Cow
不是,因为它有一个用户声明的构造函数。
适用于聚合但不适用于非聚合的东西被指定为初始化器(相同的 cppreference 页面):
Swan s{.x=3}; // OK
Cow c{.x=4}; // Error: Cow is not an aggregate
TL;DR:我不知道你的两个Dog
s 之间的区别,但一般来说,用户声明的构造函数的存在会有所不同。