mad*_*ada 1 c++ default-constructor c++20
我从cppreference发现了这个例子:
\n...\n\nstruct T3\n{\n int mem1;\n std::string mem2;\n T3() {} // user-provided default constructor\n}\n\n...\nRun Code Online (Sandbox Code Playgroud)\n此示例清楚地表明给定的构造函数是用户提供的构造函数,因为它在第一个声明中没有显式默认或删除;根据 [dcl.fct.def.default]/5:
\n\n\n[..] 如果函数是用户声明的并且在其第一次声明时未\n显式默认或删除,则该函数是用户提供的 [..]
\n
现在,根据 [dcl.init.aggr]/1
\n\n\n聚合是一个数组或一个类(第 11 条)
\n\n
\n- (1.1) \xe2\x80\x94 没有用户声明或继承的构造函数 (11.4.5),
\n- (1.2) \xe2\x80\x94 没有私有或受保护的直接非静态数据成员 (11.8),
\n- (1.3) \xe2\x80\x94 无虚函数 (11.7.3),以及
\n- (1.4) \xe2\x80\x94 无虚拟、私有或受保护的基类 (11.7.2)。
\n
看来我的类满足上述所有要求,成为一个聚合,包括点 (1.1),因为给定的构造函数不是用户声明的。
\n那么为什么下面的代码格式错误(在带有 c++20 标志的 g++12.2 上测试):
\nstatic_assert(std::is_aggregate<T3>::value); // fail\nRun Code Online (Sandbox Code Playgroud)\n为什么静态断言失败?
\n因为用户提供的构造函数是用户声明的构造函数。
它就在您引用的部分中:
[..] 如果函数是用户声明的并且在第一次声明时未显式默认或删除,则该函数是用户提供的 [..]
只有用户声明的构造函数才能成为用户提供的构造函数。当用户声明的构造函数在第一次声明时未显式默认或删除时,该构造函数就是用户提供的。
T3() {} // I user-provided, user-declared
T3() = default; // II user-declared, not user-provided
T3() = delete; // III user-declared, not user-provided
Run Code Online (Sandbox Code Playgroud)
术语可能有点令人困惑。所有 3 个都声明一个默认构造函数(可以不带参数调用的构造函数)。只是II一个默认的构造函数(定义由编译器生成)。
PS:感谢@John 也澄清了这一点
T3(); // IV user-declared, user-provided
Run Code Online (Sandbox Code Playgroud)
是用户声明和用户提供的,即使稍后它可能通过以下方式定义
T3::T3() = default;
Run Code Online (Sandbox Code Playgroud)
因为根据定义,它是用户提供的(它是用户声明的,并且)它在第一次声明时没有显式默认或删除。
| 归档时间: |
|
| 查看次数: |
242 次 |
| 最近记录: |