C++11初始化语法问题(使用gcc 4.5 / 4.6)

4
以下C++11代码存在什么问题:
struct S
{
    int a;
    float b;
};

struct T
{
    T(S s) {}
};

int main()
{
    T t(S{1, 0.1});  // ERROR HERE
}

gcc在指定的行数上报错(我尝试了gcc 4.5和实验版本的gcc 4.6)

这是不是无效的C++11代码,还是gcc的实现不完整?

编辑:以下是编译器错误:

test.cpp: In function int main():
test.cpp:14:10: error: expected ) before { token
test.cpp:14:10: error: a function-definition is not allowed here before { token
test.cpp:14:18: error: expected primary-expression before ) token
test.cpp:14:18: error: expected ; before ) token

后者通常是这种情况 - 特别是对于GCC4.5.x。 GCC4.6.x更完整,但也存在错误。如果可能的话,请进行更新。 - marko
2个回答

3
根据N2640提案,你的代码应该能够正常工作;需要创建一个临时S对象。g++似乎尝试将此语句解析为一个声明(t函数期望S),所以我认为这是一个错误。

0
似乎在没有括号的情况下调用构造函数是错误的,而这似乎可行:
struct S
{
    int a;
    float b;
};

struct T
{
    T(S s) {}
};

int main()
{
    T t(S({1, 0.1}));  // NO ERROR HERE, due to nice constructor parentheses
    T a({1,0.1}); // note that this works, as per link of Martin.
}

从逻辑上讲(至少对我来说是这样:s),你的示例似乎不起作用。将S替换为vector<int>会得到相同的结果。

vector<int> v{0,1,3}; // works
T t(vector<int>{0,1,2}); // does not, but
T t(vector<int>({0,1,2})); // does

难道这不是因为 T a({1,0.1}); 能够工作的同样原因吗?也就是说,T t(vector<int>({0,1,2})); 只是在调用 vector<int> 的拷贝构造函数吗? - dvide
好的,你可以在这里做两件事情:要么插入一些括号,要么发送一封邮件给GCC邮件列表来讨论这个问题。我看到的主要问题是有很多关于这个功能的提案和附录,而我不知道GCC想要实现哪一个... - rubenvb
@dvide 对的。T a({1, 0.1}) 调用了 T 的拷贝/移动构造函数,并通过一个临时对象初始化该构造函数的(引用)参数,好像是通过 T tmp = {1, 0.1} 进行初始化一样。如果你使用 S({1, 0.1}) 而不是 S{1, 0.1},那么你只是增加了一个无用的拷贝/移动构造函数调用,而没有直接初始化对象成员。 - Johannes Schaub - litb

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接