我应该将编译器生成的构造函数标记为constexpr吗?

Me *_*d I 30 c++ c++11

这样做有什么区别:

X() = default;
Run Code Online (Sandbox Code Playgroud)

constexpr X() = default;
Run Code Online (Sandbox Code Playgroud)

默认构造常量表达式中的类工作正常,这两个例子之间有区别吗?我应该使用一个吗?

Lig*_*ica 31

因为隐式构造函数实际上就constexpr在你的情况下......

[C++11: 12.1/6]: [..]如果用户编写的默认构造函数满足constexpr构造函数(7.1.5)的要求,则隐式定义的默认构造函数为constexpr.[..]

[C++11: 7.1.5/3]:constexpr函数的定义应满足以下约束:

  • 它不应是虚拟的(10.3);
  • 其返回类型应为字面类型;
  • 每个参数类型都应是文字类型;
  • 它的函数体应该是 = delete,= default或者只包含 复合语句
    • 空语句,
    • static_assert申述
    • typedef声明和别名声明,没有定义类或枚举,
    • 使用声明,
    • 使用指令,
    • 而且只有一个退货声明;
  • 初始化返回值(6.6.3,8.5)时使用的每个构造函数调用和隐式转换都应该是常量表达式(5.19)中允许的那些之一.

......声明实际上是等同的:

[C++11: 8.4.2/2]:显式默认函数constexpr只有在它被隐式声明为声明时才可以声明constexpr,并且只有 在与隐式声明的异常规范兼容(15.4)时才可以有明确的异常规范.如果函数在其第一个声明中明确默认,

  • 它隐含地被认为是constexpr隐含的声明是,
  • 它隐含地被认为具有相同的异常规范,就好像它已被隐式声明(15.4),和
  • 对于复制构造函数,移动构造函数,复制赋值运算符或移动赋值运算符,它应具有与隐式声明的相同的参数类型.

所以要么 - 这没关系.

在一般情况下,如果你肯定想要一个构造函数constexpr,那么保留关键字是明智的,这样如果它不符合标准,你至少会得到一个编译器错误; 如果constexpr不知道它,你可能会得到一个非构造函数.