C++ C++;自引用数组?

C++ C++;自引用数组?,c++,C++,我无意中通过数组中的自引用在程序中创建了一个bug。这是一个非常简化的演示程序,概念类似: #include <iostream> using namespace std; int kTest[] = { kTest[0] }; int main() { cout << kTest[0] << endl; } #包括 使用名称空间std; int kTest[]={ kTest[0] }; int main(){ 库特 与类似,但不完全相

我无意中通过数组中的自引用在程序中创建了一个bug。这是一个非常简化的演示程序,概念类似:

#include <iostream>
using namespace std;

int kTest[] = {
    kTest[0]
};

int main() {
    cout << kTest[0] << endl;
}
#包括
使用名称空间std;
int kTest[]={
kTest[0]
};
int main(){
库特
与类似,但不完全相同

int x = x;
如果在函数中本地声明,它将是未定义的行为


kTest
是一个全局变量时,它似乎定义得很好。有关更多详细信息,请参阅。

我不确定这是否未定义。引用当前:

[basic.start.static]/3

如果未执行常量初始化,则使用静态 存储持续时间([basic.stc.static])或线程存储持续时间 ([basic.stc.thread])一起初始化为零([dcl.init]), 零初始化和常量初始化称为静态初始化 初始化;所有其他初始化都是动态初始化。 静态初始化应在任何动态初始化发生之前进行


在我看来,当动态初始化开始时,
kTest
已经初始化为零,因此它可能被定义为初始化为
0

hmm。全局
int
s是零初始化的,因此我想知道是否因此它是合法的。这与没有太大区别。为什么会是一个错误?
kTest
由于使用点的不同,Globals通常被初始化为0,但由于您正在手动初始化它,因此它会使用第0个元素进行初始化——这是垃圾元素,因为它仍在初始化过程中。这实际上是生成所谓“垃圾”的真实代码吗?因为此初始化是动态的(假设初始值设定项不是一个常量表达式),
kTest
在静态阶段保证为零初始化。我认为只有当
kTest[…]
中的索引等于或大于
kTest
中的条目数时,这才是形式上的UB(例如,如果使用
kTest[5]
在上面,不添加至少5个条目)这应该不仅仅是一个观点,不是吗?或者是它是否是UB没有被标准定义?它是否可以被未指定?我想它类似于这样:
int x;x=x;
@Carcigenicate,我在C++11标准中看到了
int x=x;
被讨论过,但我找不到任何关于OP情况的东西。我不是这样的ure,如果你看我能说的话,这应该是零初始化的。你的解释是有意义的。
g++
在全局定义时没有抱怨
int x=x;
但在函数中定义时抱怨。为什么你认为OP的全局初始化是动态的?如果我有
static int a[]={1}仅静态初始化的。
a[0]
未初始化为0(静态),然后再次初始化为1(动态)@PaulJ.Lucas:零初始化和常量初始化一起称为静态初始化;所有其他初始化都是动态初始化。@Paul J.Lucas:因为它不是零初始化,并且不满足常量初始化的要求。这会立即使它成为动态的。
static int a[]={1}
示例完全不同。然而,从概念上讲,它实际上分为两个阶段:零初始化,然后是1初始化。但这两个阶段都是静态初始化。当存在常量初始化时,是C++17决定消除不必要的零初始化。请参阅我相信您的解释保留是正确的。
int x = x;