c ++ 11 struct initialization compilation error

时间:2013-08-12 09:54:39

标签: c++ c++11

struct SS {int a; int s;};

int main ()
{
   vector<SS> v;
   v.push_back(SS{1, 2});
}

可以编译代码而不会出现任何错误。但是,当在类中初始化struct时,我得到了编译错误。谁能解释一下呢?

struct SS {int a = 0; int s = 2;};

错误:

In function ‘int main()’:
error: no matching function for call to ‘SS::SS(<brace-enclosed initializer list>)’
     v.push_back(SS{1, 2});
                        ^
note: candidates are:
note: constexpr SS::SS()
 struct SS {int a = 0; int s = 2;};
        ^
note:   candidate expects 0 arguments, 2 provided
note: constexpr SS::SS(const SS&)
note:   candidate expects 1 argument, 2 provided
note: constexpr SS::SS(SS&&)
note:   candidate expects 1 argument, 2 provided

3 个答案:

答案 0 :(得分:32)

在C ++ 11中,当您在声明时使用非静态数据成员初始化时,就像在此处一样:

struct SS {int a = 0; int s = 2;};

您将课程设为非聚合。这意味着您无法再初始化这样的实例:

SS s{1,2};

要使此初始化语法适用于非聚合,您必须添加一个双参数构造函数:

struct SS 
{
  SS(int a, int s) : a(a), s(s) {}
  int a = 0; 
  int s = 2;
};

此限制已在C ++ 14中解除。

请注意,您可能希望为该类添加默认构造函数。用户提供的构造函数的存在会禁止编译器生成默认值。

参见相关阅读here

答案 1 :(得分:4)

使用默认成员初始化程序会使类/结构为 非聚合:

§8.5.1聚合

聚合是一个数组或类(第9节),没有用户提供的构造函数(12.1),没有用于非静态数据成员的大括号或等于初始化程序(9.2),没有私有或受保护的非静态数据成员(第11条),没有基类(第10条),也没有虚函数(10.3)。

聚合和非聚合的语义不同:

聚合(例如,数组和结构):

Initialize members/elements beginning-to-end.

<强>非聚集体:

Invoke a constructor.

v.push_back(SS{1, 2}); // Error, it tries to call SS constructor

这意味着你现在需要一个构造函数:

struct SS 
{
  SS(int a, int s) : a(a), s(s) 
  {
  }
  int a = 0; 
  int s = 2;
};

答案 2 :(得分:0)

我有同样的问题。就我而言,我有两个struct,它们都有一些构造函数,包括复制构造函数,它们都是从抽象父级继承的。

当上述建议无济于事时,我终于意识到我需要从复制构造函数中删除explicit指定符,并删除了错误。

如果另一个可怜的人花了与我一样长的时间来发现这个错误,我想分享一下。