Рассмотрим этот код в VS2015:
int a,b;
[]
{
int a; // C4456: declaration of 'a' hides previous local declaration
};
Зачем a
в лямбду дают такое предупреждение? Прекрасно компилируется в VS2013.
РЕДАКТИРОВАТЬ: Интересно, что (и неправильно), следующее не является ошибкой в VS2013:
[a]
{
int a; // No error, even if `a` is captured.
a++;
};
Первое предупреждение определенно похоже на ошибку компилятора.
Второй не ошибка, так как вы объявляете это в другом объеме. Переменная только захватывается, она не объявляется захватом.
Подумайте об объекте функции, который это может сгенерировать
class foo {
foo(int a): a(a) {}
void operator()() {
int a;
}
int a;
};
Там нет конфликта между двумя декларациями a
и так как лямбда компилируется во что-то подобное, вот почему захват не заботится о внутренней декларации.
Обновить: Это нечто совершенно отличное от
void foo(int a) {
int a;
}
потому что в случае лямбды, он будет скомпилирован в класс с operator()
и захваты будут переданы в качестве параметров конструктора, поэтому они находятся в другой области видимости.