Оновлення: як обіцяв крісло Core в нижній цитаті, код зараз неправильно сформований :
Якщо ідентифікатор в простому-захопленні з'являється як описатель-ідентифікатор параметра в лямбда-описувач «s параметра декларування-п , програма погано сформована.
Нещодавно було кілька питань щодо пошуку імен у лямбдах. Вони були вирішені N2927 :
Нова редакція більше не покладається на пошук для перенастроювання використання захоплених об'єктів. Він більш чітко заперечує інтерпретації того, що складений вислів лямбда обробляється за два проходи або що будь-які імена в цьому складному операторі можуть відповідати члену типу закриття.
Пошук завжди проводиться в контексті лямбда-виразу , ніколи не після "перетворення" в тіло функції члена типу закриття. Див. [Expr.prim.lambda] / 8 :
В лямбда-вираз «сек з'єднання-твердження дає функцію-тілу ([dcl.fct.def]) оператор виклику функції, але для цілей пошуку імен, [...], то з'єднання-заяву розглядається в контексті лямбда-вираз . [ Приклад :
struct S1 {
int x, y;
int operator()(int);
void f() {
[=]()->int {
return operator()(this->x+y); // equivalent to: S1::operator()(this->x+(*this).y)
// and this has type S1*
};
}
};
- кінцевий приклад ]
(У прикладі також ясно, що пошук не якимось чином враховує згенерований член захоплення типу закриття.)
Назва foo
не (повторно) оголошена під час захоплення; це оголошено в блоці, що охоплює вираз лямбда. Параметр foo
оголошується в блоці, який вкладений у цей зовнішній блок (див. [Basic.scope.block] / 2 , де також явно згадуються параметри лямбда). Порядок пошуку чітко від внутрішнього до зовнішнього блоків . Звідси слід вибрати параметр, тобто Кланг має рацію.
Якби ви зробили захоплення init-capture, тобто foo = ""
замість цього foo
, відповідь була б не однозначною. Це тому, що захоплення зараз фактично викликає декларацію , "блок" якої не заданий. Я обміняв це питання основним кріслом, який відповів
Це випуск 2211 (незабаром з’явиться новий список випусків на сайті open-std.org, на жаль, із просто заповнювачами для ряду питань, з яких це одне; я наполегливо працюю, щоб заповнити ці прогалини перед Kona зустріч в кінці місяця). CWG обговорював це під час нашої січневої телеконференції, і напрямок полягає в тому, щоб зробити програму неправильно сформованою, якщо ім'я захоплення також є назвою параметра.