g++11 :摆脱成员 'A::<anonymous>' 缺少的初始值设定项
g++11 : getting rid of missing initializer for member 'A::<anonymous>'
我即将发布一个代码,我不希望其中有任何警告。
目前 运行 -Wall -Wextra
尽我所能。
现在我有了这个示例代码(从生产代码中非常人为地设计):
// Type your code here, or load an example.
#include <iostream>
#include <vector>
using namespace std;
struct A {
union {
int i = 82, j;
};
int a = 98, b = 22;
};
int main() {
A p = {.a = 45};
cout << p.a << endl; // just here to prevent optimization
cout << p.i << endl; // same
return 0;
}
可以在这里测试:
Godbolt test case
然后我得到:
警告:缺少成员 'A::' [-Wmissing-field-initializers]
的初始值设定项
现在,真正的问题是 真正 缺乏初始化会产生很多后果(想想现实生活中的伤害)。
请注意,所有字段都有默认初始化。并且单元测试显示字段已正确初始化(运气?)
同样,我对这个警告感到非常不舒服。
需求:
在生产代码中,结构足够大,我不愿意用这种表示法手动初始化所有成员(并且使用许多初始化策略,它很快变得 unbearable/error 容易)
如何在不关闭 -Wextra
的情况下设法使此警告消失(同样,认为在缺少初始化的情况下会造成损坏)?
更新:
我看到了其他相关问题,但考虑到风险,我真的很想深入了解这个特殊案例。
更新 2:
阅读不同编译器的程序集,他们似乎采取了正确的行动,但只有 GCC 抱怨。
对于问题:“我的字段都初始化了吗?”
从
开始
all the fields have a default initialization
答案是:是
来源:https://en.cppreference.com/w/cpp/language/aggregate_initialization
部分:指定的初始值设定项
示例:
struct A { int x; int y; int z; };
A a{.y = 2, .x = 1}; // error; designator order does not match declaration order
A b{.x = 1, .z = 2}; // ok, b.y initialized to 0
和
struct A {
string str;
int n = 42;
int m = -1;
};
A{.m=21} // Initializes str with {}, which calls the default constructor
// then initializes n with = 42
// then initializes m with = 21
现在,如何处理警告。我能想到的:
- 将所有初始化 => 代码添加到 big
- Disable locally the warning => 同样的问题
- 不要使用
-Wall -Wextra
而是使用减号内的所有警告
-Wmissing-field-initializers
并在您的测试中添加带有 clang 完整警告和 -Werror
. 的构建
如果你的代码库不能用 clang 编译,我能想到的最后一件事是:做一个列出所有“不需要的警告”的脚本和 运行 你的构建,如果你有一个新的警告: 修理它。它很丑,而且扩展性不好。
我即将发布一个代码,我不希望其中有任何警告。
目前 运行 -Wall -Wextra
尽我所能。
现在我有了这个示例代码(从生产代码中非常人为地设计):
// Type your code here, or load an example.
#include <iostream>
#include <vector>
using namespace std;
struct A {
union {
int i = 82, j;
};
int a = 98, b = 22;
};
int main() {
A p = {.a = 45};
cout << p.a << endl; // just here to prevent optimization
cout << p.i << endl; // same
return 0;
}
可以在这里测试: Godbolt test case
然后我得到: 警告:缺少成员 'A::' [-Wmissing-field-initializers]
的初始值设定项现在,真正的问题是 真正 缺乏初始化会产生很多后果(想想现实生活中的伤害)。
请注意,所有字段都有默认初始化。并且单元测试显示字段已正确初始化(运气?)
同样,我对这个警告感到非常不舒服。
需求:
在生产代码中,结构足够大,我不愿意用这种表示法手动初始化所有成员(并且使用许多初始化策略,它很快变得 unbearable/error 容易)
如何在不关闭 -Wextra
的情况下设法使此警告消失(同样,认为在缺少初始化的情况下会造成损坏)?
更新:
我看到了其他相关问题,但考虑到风险,我真的很想深入了解这个特殊案例。
更新 2:
阅读不同编译器的程序集,他们似乎采取了正确的行动,但只有 GCC 抱怨。
对于问题:“我的字段都初始化了吗?”
从
开始all the fields have a default initialization
答案是:是
来源:https://en.cppreference.com/w/cpp/language/aggregate_initialization
部分:指定的初始值设定项 示例:
struct A { int x; int y; int z; };
A a{.y = 2, .x = 1}; // error; designator order does not match declaration order
A b{.x = 1, .z = 2}; // ok, b.y initialized to 0
和
struct A {
string str;
int n = 42;
int m = -1;
};
A{.m=21} // Initializes str with {}, which calls the default constructor
// then initializes n with = 42
// then initializes m with = 21
现在,如何处理警告。我能想到的:
- 将所有初始化 => 代码添加到 big
- Disable locally the warning => 同样的问题
- 不要使用
-Wall -Wextra
而是使用减号内的所有警告-Wmissing-field-initializers
并在您的测试中添加带有 clang 完整警告和-Werror
. 的构建
如果你的代码库不能用 clang 编译,我能想到的最后一件事是:做一个列出所有“不需要的警告”的脚本和 运行 你的构建,如果你有一个新的警告: 修理它。它很丑,而且扩展性不好。