Являются ли следующие два фрагмента кода одинаковыми независимо от типа и квалификаторов response
, считая, что конструктор копирования и оператор назначения копирования не имеют побочных эффектов?Является ли лямбда с инициализатором для себя эквивалентной лямбда без инициализатора?
auto foo = [response]() {
do_something(response);
};
И
auto foo = [response = response]() {
do_something(response);
};
Казалось бы, что они делают то же самое – скопировать ответ объект –, но в некоторых случаях, только вторая версия компилирует.
Вот пример программы для демонстрации проблемы:
#include <memory>
using namespace std;
void do_something() {
}
int main() {
auto au = [](auto callback) {
callback();
};
auto x = [&au](shared_ptr<int> response) {
au([response = move(response)]() mutable {
auto foo = [response/* = response*/]() { // uncomment and it will work
do_something();
};
});
};
x(make_shared<int>(100));
}
Кажется, что response
должен быть std::shared_ptr
для этого вопроса, чтобы это произошло, но я не знаю, почему. Я понимаю, что копирование shared_ptr
не копирует фактический ресурс (т. Е. int
), но я не вижу, как это может привести к сбою компиляции кода. Я всегда считал, что два лучших фрагмента кода делают то же самое.
Если это необходимо, я использую MSVC 2015 и скомпилировал его с помощью Debug x86, но я думаю, что его компиляция как Release или как x64 дает тот же результат.
Прокомментированная версия работает для меня как на gcc, так и на clang. Это может быть ошибка компилятора. – user2079303
[Есть случаи] (http://stackoverflow.com/a/36188986/3953764), где синтаксис, используемый для захвата переменной, имеет значение, ни один из них, похоже, не применяется к вашему коду –
Существует разница в том, как работает поиск имени для этих двух форм, не уверен, что это вызывает проблему с MSVC. – TartanLlama