我可以忽略gcc警告:'Foo :: m_bar'应该在成员初始化列表中初始化[-Weffc ++]

qdi*_*dii 19 c++ gcc warnings compilation c++11

struct Bar
{
    Bar() {}
};


struct Foo
{
    Foo() = default;
    Bar m_bar;
};

int main()
{
    Foo foo;
}
Run Code Online (Sandbox Code Playgroud)

使用C++ 11 default关键字和gcc警告时-Weffc++,gcc输出:

警告:'Foo :: m_bar'应该在成员初始化列表中初始化[-Weffc ++]

忽略这个警告是否安全?我应该向gcc提交错误吗?

小智 29

您可以忽略或取消警告.这是对有效C++指南之一的误解.指南说更喜欢初始化到分配,但在您的示例中,m_bar将初始化.你的代码是正确的.

来源:Jonathan Wakely在GCC的bug追踪器中:

#Item 12:首选初始化为构造函数中的赋值.

替换为第4项:"确保在使用对象之前对其进行初始化",并且G ++无论如何都会错误解释原始项目并警告任何 没有mem-initializer的成员,这非常烦人:没有必要初始化std :: string,它有一个完全安全的默认构造函数.我对PR 2972​​的-Wmeminit补丁应该替换此项目的当前警告,因为它只会警告构造函数未初始化的成员.

(因为它是一个已知问题,所以不需要再将它报告为bug.)


Dim*_*nek 5

可以忽略这个警告吗?是.

忽略这个警告是个好主意吗?要看(*)

你应该向gcc提交一个bug吗?没有(*)

(*)

  • default实际上构造函数初始化m_bar很好,你可以测试一下
  • 有点奇怪,g ++没有得到它
  • 你选择了非常详细的警告设置
  • 警告不是关于代码的正确性,而是关于样式
  • 你不能纠正这个并保留Foo的默认构造函数和Bar的自定义构造函数

man g++,部分-Weffc ++

警告Scott Meyers的Effective C++书籍违反以下风格指南:

  • 第11项:为具有动态分配内存的类定义复制构造函数和赋值运算符.
  • 第12项:首选初始化为构造函数中的赋值.
  • 第14项:在基类中使析构函数虚拟化.
  • 第15项:让"operator ="返回对*this的引用.
  • 第23项:当你必须返回一个物体时,不要试图返回一个参考.

还警告Scott Meyers的"更有效的C++"一书中违反以下风格指南:

  • 第6项:区分增量和减量运算符的前缀和后缀形式.
  • 第7项:永远不要超载"&&","││"或",".

选择此选项时,请注意标准库标题不符合所有这些准则.