我一直在使用c ++ 0x一段时间,并且非常享受新的lamba功能设施。我习惯于在我的lambda声明中指定[=]来表示我想通过值将外部作用域的变量传递给我的lambda。
然而,今天我遇到了一个非常奇怪的lambda问题。我注意到在for_each期间通过值将外部范围的映射传递给lamba奇怪地工作。这是一个显示问题的例子:
void LambdaOddnessOne ()
{
map<int, wstring> str2int;
str2int.insert(make_pair(1, L"one"));
str2int.insert(make_pair(2, L"two"));
vector<int> numbers;
numbers.push_back(1);
numbers.push_back(2);
for_each ( numbers.begin(), numbers.end(), [=]( int num )
{
//Calling find() compiles and runs just fine
if (str2int.find(num) != str2int.end())
{
//This won't compile... although it will outside the lambda
str2int[num] = L"three";
//Neither will this saying "4 overloads have no legal conversion for 'this' pointer"
str2int.insert(make_pair(3, L"three"));
}
});
}
可以从lamba内部调用许多map的方法(例如find),但是当它们在lamba之外编译得很好时,许多其他方法会导致编译错误。
尝试使用[运算符导致:
error C2678: binary '[' : no operator found which takes a left-hand operand of type 'const std::map<_Kty,_Ty>' (or there is no acceptable conversion)
尝试使用.insert函数导致:
error C2663: 'std::_Tree<_Traits>::insert' : 4 overloads have no legal conversion for 'this' pointer
有没有人理解这种不一致的行为?这只是MS编译器的一个问题吗?我没有尝试过任何其他人。
答案 0 :(得分:7)
FYI [=]
按价值捕获,IIRC [&]
通过引用捕获。
答案 1 :(得分:4)
默认情况下,lambda的函数调用运算符是const(因此您无法修改按值传递的映射),但您可以通过编写mutable
使其成为非const:
for_each ( numbers.begin(), numbers.end(), [=]( int num ) mutable
{
// ...
有关详细信息,请参阅why does C++0x's lambda require “mutable” keyword for capture-by-value, by default?