成员结构可以从构造函数初始化器列表中的零初始化而不调用memset? [英] Can a member struct be zero-init from the constructor initializer list without calling memset?
问题描述
假设我有以下结构声明(没有构造函数的简单结构体)。
struct Foo
{
int x;
int y;
int z;
char szData [DATA_SIZE];
};
现在我们假设这个结构是C ++类的成员,如下:
class CFoobar
{
Foo _foo;
public:
CFoobar();
};
如果我声明CFoobar的构造函数如下:
CFoobar :: CFoobar()
{
printf(_ foo = {%d,%d,%d} \\\
,_foo.x, _foo.y,_foo.z);
for(int x = 0; x< 100; x ++)
printf(%d\\\
,_foo.szData [x]);
}
正如你所期望的,当CFoobar的构造函数运行时,垃圾数据被打印出来显然,容易修复的是memset或ZeroMemory& _foo。这是我一直做的...
然而,我没有注意到如果添加_foo到构造函数的初始化列表,没有参数如下:
CFoobar :: CFoobar()
/ pre>
:_foo()
{
这似乎是清除_foo的成员变量。至少这是g ++在linux上的情况。
现在这里是我的问题:这是标准C ++,还是这个编译器特定的行为?
如果是标准行为,有人可以从官方来源引用我的参考资料吗?任何有关使用更复杂的结构和类的隐式零初始化行为的陷阱?
解决方案根据标准。 12.6.2 [class.base.init] / 3:如果省略了em-initializer 的 expression-list ,则基类或成员子对象是 value-initialized 。
但是,如果
Foo
不是POD类型,但仍然没有用户声明的构造函数(例如它有一个std :: string
类型),那么一些非常流行的编译器将无法正确地初始化<当您使用
POD成员的 ()作为构造函数initializer-list中的初始化器。时,我知道的所有编译器都能正确执行
Let's say I have the following structure declaration (simple struct with no constructor).
struct Foo { int x; int y; int z; char szData[DATA_SIZE]; };
Now let's say this struct is a member of a C++ class as follows:
class CFoobar { Foo _foo; public: CFoobar(); };
If I declare CFoobar's constructor as follows:
CFoobar::CFoobar() { printf("_foo = {%d, %d, %d}\n", _foo.x, _foo.y,_foo.z); for (int x = 0; x < 100; x++) printf("%d\n", _foo.szData[x]); }
As you would expect, when CFoobar's constructor runs, garbage data gets printed out Obviously, the easy fix is to memset or ZeroMemory &_foo. It's what I've always done...
However, I did notice that if add _foo to the constructor's initialization list with no parameters as follows:
CFoobar::CFoobar() : _foo() {
That this appears to zero-out the member variables of _foo. At least that was the case with g++ on linux.
Now here's my question: Is this standard C++, or is this compiler specific behavior?
If it's standard behavior, can someone quote me a reference from an official source? Any "gotchas" in regards to implicit zero-init behavior with more complicated structs and classes?
解决方案Yes, this is defined behaviour according to the standard. 12.6.2 [class.base.init] / 3 : "if the expression-list of the mem-initializer is omitted, the base class or member subobject is value-initialized."
Be warned, though, if
Foo
wasn't a POD-type but still had no user-declared constructor (e.g. it had astd::string
type) then some very popular compilers would not correctly value-initialize it.All compilers that I know of do correctly perform value-initialization of POD members when you use
()
as the initializer in a constructor initializer-list.这篇关于成员结构可以从构造函数初始化器列表中的零初始化而不调用memset?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!