为什么这个片段使用统一初始化编译g++4.6而不是g++4.7

Why does this snippet using uniform initialization compile with g++4.6 but not g++4.7?

本文关键字:g++4 编译 初始化 片段 为什么      更新时间:2023-10-16

请注意,派生的使用C++11统一初始化语法来调用基类构造函数。

class base
{
    protected:
        base()
        {}
};
class derived : public base
{
    public:
        derived()
            : base{} // <-- Note the c++11 curly brace syntax
                     // using uniform initialization. Change the
                     // braces to () and it works.
        {}
};
int main()
{
    derived d1;
    return 0;
}

g++4.6编译了这个,但是g++4.7没有:

$ g++-4.7 -std=c++11 -Wall -Wextra -pedantic curly.cpp -o curly
curly.cpp: In constructor ‘derived::derived()’:
curly.cpp:4:13: error: ‘base::base()’ is protected
curly.cpp:19:24: error: within this context

怎么回事?

更新1:它还使用clang++-3.1
编译而没有警告更新2:看起来确实是一个编译器错误。它显然在GCC 4.7.3中得到了修复。

Paolo Carlini,GCC/libstdc++的贡献者,确认这是一个错误/回归。

这可能是因为在版本4.7中添加了C11显式覆盖控制。

用icpc编译它(英特尔编译器用11.1->12.1版本测试)会给出:

-bash-3.2$ icpc -std=c++0x test.c 
test.c(15): error: expected a declaration
          {}
          ^
test.c(12): error: expected a "("
              : base{} // <-- Note the c++11 curly brace syntax
                    ^
compilation aborted for test.c (code 2)

编辑:不过话说回来,c++11在icpc中还没有完全实现http://software.intel.com/en-us/articles/c0x-features-supported-by-intel-c-compiler/

与g相同++http://gcc.gnu.org/gcc-4.7/cxx0x_status.html

它清楚地表明它仍然是实验性的,所以很有可能出现错误。

我发现了这个:

草案指出,初始化引用的初始化器列表不是通过直接绑定完成的,而是通过首先在初始化器列表中的元素外构造一个临时的,然后将目标引用绑定到该临时的

因此,它可能会因为基{}创建的临时操作是通过受保护的构造函数完成的而窒息。