繁体   English   中英

我应该如何从 C++ 正确初始化 C 结构?

[英]How should I properly initialize a C struct from C++?

我在 C++ 文件中有以下代码:

#include <sys/socket.h>

// ...
void someFunc() {
    struct msghdr msg = {0};  // <<< Uninitialized member here
}

当我使用g++使用-Wall -Wextra进行编译时,我收到警告:

error: missing initializer for member 'msghdr::msg_namelen'
...same for several other fields

我的问题是:我无法显式初始化所有字段,因为我不知道struct msghdr中将存在哪些字段(跨平台)。 该结构没有默认构造函数,因为它是 C 结构。 我的印象是= {0}表单导致所有字段的零初始化(这对我来说很好),但g++错误消息表明不是。

我在这里有什么选择?

void someFunc()
{
    msghdr msg = {};  // <<< All members zero-initialized
}

g ++ -Wextra警告级别是恕我直言不是很有用。

您所拥有的代码对于称为POD(Plain Old Data)的标准“C结构”也是正式的。 但是你的代码用0显式初始化第一个成员。这不一定适用于非POD的聚合,例如std::string作为第一个成员,而pure {}也适用于此。

顺便说一句,通常像你正在处理的那个POD有一个字节数作为第一个成员,然后你可以这样做......

void foo()
{
    SomePODStruct o = {sizeof(o)};    // The other members zero-initialized.
}

也许添加字节计数成员为第一个的STATIC_ASSERT (偏移量为0)。

干杯&hth。,

这应该工作:

memset(&msg, 0, sizeof(msg));

导致这种情况的特定警告标志是-Wmissing-field-initializers ,它作为-Wextra一部分-Wextra 因此,避免此(伪造)警告的最简单方法是使用-Wno-missing-field-initializers

如果你不能忍受警告和/或不想禁用警告,那么我认为它必须通过例如memset显式初始化:

memset(&msg, 0, sizeof(msg));

也许如果你不想使用默认构造函数,你可以简单地使用预处理器函数,如:

#ifdef LINUX
//init for linux
#endif

#ifdef WINDOWS
//init for windows
#endif

等等

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM