编译器生成的默认构造函数是否会将std :: array中的指针初始化为nullptr?

问题描述 投票:1回答:3

如果给出下面的代码,编译器应该生成应该调用Node()std::array<Node *, 100>()是正确的,std::array<Node *, 100> children {};应该初始化所有100个指向nullptr的指针。

旁注:我知道如果我使用struct Node { int value; std::array<Node *, 100> children; } ,我可以做到这一点,但我并不是想让我的代码工作(它已经做到了),我试图确保它不会偶然发生。

struct Node
{
    int value;
    std::array<Node *, 100> children;
}

struct Node
{
    Node() : children() {}
    int value;
    std::array<Node *, 100> children;
}

更新:

这里的指针是垃圾:

struct Node
{
    int value;
    std::array<Node *, 100> children {};
}

struct Node
{
    Node() : children{} {}
    int value;
    std::array<Node *, 100> children;
}

这里的指针是nullptr:

cppreference

如果我错了,请纠正我。

c++ arrays initialization std
3个回答
5
投票

std::array的构造函数上引用std::array<Node *, 100> children;

按照聚合初始化规则初始化数组(请注意,默认初始化可能会导致非类T的不确定值)

通过声明像int这样的变量,可以调用默认构造函数。并且,根据初始化规则,POD(chardoublenullptr,指针......)不是默认初始化的。所以不,如果不使用聚合初始化,则不会使用std::array<Node *, 100> children; 初始化数组。

聚合初始化

std::array<Node *, 100> children{}
std::array<Node *, 100> children = {};

调用默认构造函数,但没有给出聚合初始值设定项,因此不会发生聚合初始化。然而

{}

不仅调用默认构造函数,还执行聚合初始化。在这种情况下,汇总Node x; std::array<Node *, 100> children = {&x}; 只是空的。并且,遵循聚合初始化规则,如果初始化程序的数量少于数据成员,则每个未初始化的成员都将默认初始化。所以

x

例如,将使用指向nullptr的指针初始化第一个数组元素,并且每个连续元素将默认初始化为this answer


1
投票

根据std::arraystd::array<Node *, 100> children; // pointers are uninitialized 指针的默认初始化不会初始化它包含的指针,它们的值将是不确定的。

nullptr

但是,您可以使用值初始化来初始化包含std::array的所有指针。在std::array<Node *, 100> children {}; // pointers are all null 上,这具有初始化数组中每个值的值的效果,这反过来对每个指针进行零初始化。

Node::Node() : children{/* value init array */} {/* empty c'tor body */}

在成员初始化列表中,您还可以执行以下操作:

nullptr

0
投票

在为指针指定值之前,默认情况下它指向“垃圾”地址。编译器不会为它们分配默认值documentation for std::array。实际上,它没有为指针分配任何“默认”值。 编辑: 来自cppreference nullptr

请注意,默认初始化可能会导致非类T的不确定值

因此,如果使用默认构造函数,则需要自己为每个元素分配值qazxswpoi。

© www.soinside.com 2019 - 2024. All rights reserved.