【发布时间】:2015-04-03 19:44:43
【问题描述】:
考虑一下这个 C++11 代码 sn-p:
#include <iostream>
#include <set>
#include <stdexcept>
#include <initializer_list>
int main(int argc, char ** argv)
{
enum Switch {
Switch_1,
Switch_2,
Switch_3,
Switch_XXXX,
};
int foo_1 = 1;
int foo_2 = 2;
int foo_3 = 3;
int foo_4 = 4;
int foo_5 = 5;
int foo_6 = 6;
int foo_7 = 7;
auto get_foos = [=] (Switch ss) -> std::initializer_list<int> {
switch (ss) {
case Switch_1:
return {foo_1, foo_2, foo_3};
case Switch_2:
return {foo_4, foo_5};
case Switch_3:
return {foo_6, foo_7};
default:
throw std::logic_error("invalid switch");
}
};
std::set<int> foos = get_foos(Switch_1);
for (auto && foo : foos) {
std::cout << foo << " ";
}
std::cout << std::endl;
return 0;
}
无论我尝试什么编译器,似乎都处理不正确。这让我觉得我做错了什么,而不是跨多个编译器的常见错误。
clang 3.5 输出:
-1078533848 -1078533752 134518134
gcc 4.8.2 输出:
-1078845996 -1078845984 3
gcc 4.8.3 输出(编译在http://www.tutorialspoint.com):
1 2 267998238
gcc(未知版本) 输出(编译于http://coliru.stacked-crooked.com)
-1785083736 0 6297428
问题似乎是由于使用std::initializer_list<int> 作为 lambda 的返回值引起的。将 lambda 定义更改为 [=] (Switch ss) -> std::set<int> {...} 时,返回值正确。
请帮我解开这个谜。
【问题讨论】:
-
正如我在下面的回答中指出的那样,具有讽刺意味的是,
initializer_list的最终提案中指出了这种确切的情况并将其视为不太可能出现的问题。
标签: c++ c++11 lambda initializer-list