在自己的初始化器中使用变量

Use of variable in own initializer

[basic.scope.pdecl]/1 of the C++20 standard draft had the following (non-normative) example in a note (partial quote from before the merge of pull request 3580,请参阅此问题的答案):

unsigned char x = x;

[...] x is initialized with its own (indeterminate) value.

这实际上在 C++20 中具有明确定义的行为吗?


通常,T x = x; 形式的自初始化具有未定义的行为,因为 x 的值在初始化完成之前是 不确定的。评估不确定值通常会导致未定义的行为([basic.indent]/2), but there is a specific exception in [basic.indent]/2.3 允许从具有不确定值的左值 unsigned char 直接初始化 unsigned char 变量(导致使用不确定值进行初始化)。

因此,这本身不会导致未定义的行为,但对于其他类型 T 不是无符号窄字符类型或 std::byte,例如int x = x;。这些注意事项也适用于 C++17 及之前的版本,另请参阅底部的链接问题。

但是,即使对于 unsigned char x = x;,当前草案的 [basic.lifetime]/7 表示:

Similarly, before the lifetime of an object has started [...] using the properties of the glvalue that do not depend on its value is well-defined. The program has undefined behavior if:

  • the glvalue is used to access the object, or

  • [...]

这似乎暗示示例中 x 的值只能在其生命周期内使用。

[basic.lifetime]/1 说:

[...]

The lifetime of an object of type T begins when:

  • [...] and
  • its initialization (if any) is complete (including vacuous initialization) ([dcl.init]),

[...]

因此x的生命周期只有在初始化完成后才开始。但在引用的示例中,x 的值在 x 的初始化完成之前使用。因此,使用具有未定义的行为。

我的分析是否正确?如果正确,是否会影响初始化前使用的类似情况,例如

int x = (x = 1);

据我所知,哪些在 C++17 及之前的版本中也有明确定义?


请注意,在 C++17(最终草案)中,生命周期开始的第二个要求是 different:

  • if the object has non-vacuous initialization, its initialization is complete,

由于 x 根据 C++17 的定义(但不是当前草案中的定义)会进行空洞的初始化,因此当在上面给出的示例中的初始化程序中访问它时,它的生命周期就已经开始了因此在这两个示例中,由于 C++17 中 x 的生命周期,没有未定义的行为。

C++17之前的写法又不一样了,结果一样


问题不在于使用不确定值时的未定义行为,这在例如以下问题:

这是作为 editorial issue. It was forwarded to CWG for (internal) discussion. Approximately 24 hours later, the person who forwarded the issue created a pull request 打开的,它修改了示例以明确这是 UB:

Here, the initialization of the second \tcode{x} has undefined behavior, because the initializer accesses the second \tcode{x} outside its lifetime\iref{basic.life}.

该 PR 已添加,问题已关闭。因此,显而易见的解释(由于访问生命周期尚未开始的对象而导致的 UB)似乎很明显是预期的解释。委员会 的意图似乎是 使这些结构失效,并且已更新标准的非规范性文本以反映这一点。