结构初始化中隐式复制构造函数出错

时间:2015-12-22 19:04:06

标签: c++

我提出了一个问题,根据我对C ++的了解,我无法解释。

我有一个类,它对类型X的结构进行常量引用,但是当我传递一个X类型的参数(我之前初始化)时,我从编译器得到一个错误,说它无法转换为X的成员的第一个成员。这对我没有任何意义。

clang和g ++中的错误类似,这让我觉得我错过了一些令人震惊的东西。

error: no viable conversion from 'const Foo::X' to 'Foo::FooTypes'

为什么要尝试从X转换为FooTypes,这是Z的第一个成员?

class Foo {
public:
    enum FooTypes {
        JPEG
    };
    struct Z {
        FooTypes type;
        int a;
    };

    struct X {
        Z caps;
        double host_address;
    };
    Foo(const X& x);
private:
    const X x;
};

Foo::Foo(const Foo::X& x) :
                x{x}    {
}
int main() {
    Foo::X new_x = {
        {Foo::JPEG, 1}, 1.58 };
    Foo *s = new Foo(new_x);
    delete s;
    return 0;
}

1 个答案:

答案 0 :(得分:3)

您应该使用圆括号而不是大括号:

...
    const X m_x;
};
Foo::Foo(const Foo::X& x) :
    m_x(x) {
}
...

这里是列表初始化:

...
m_x{x.caps, x.host_address}
...

修改 @PauloNeves 我刚刚找到了Bjarne Stroustrup的文档http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2008/n2640.pdf,其中包含下一个定义:

  

"初始化列表的一般概念" (正如多年所讨论的那样   在EWG中)是允许使用括号括起来的表达式列表   所有允许初始化器的上下文。以下列表被取消   来自N2532:

     
      
  • 变量初始化;例如,X x {v};
  •   
  • 临时的初始化;例如,X {v}
  •   
  • 显式类型转换;例如x X {v};
  •   
  • 免费商店分配;例如p new X {v}
  •   
  • 回报值;例如,X f(){/ * ... * / return {v}; }
  •   
  • 论证传递;例如,void f(X); / * ... * / f({v});
  •   
  • 基础初始化;例如,Y :: Y(v):X {v} {/ * ... * /};
  •   
  • 会员初始化;例如,Y :: Y(v):mx {v} {X mx; / * ... * /};
  •   

我认为描述会员初始化就是你的情况。对我来说,它看起来像g ++ 4.9缺陷。