C ++ Почему компилятор не может генерировать код, который возвращает константную ссылку на захваченную переменную в Lambda - PullRequest
0 голосов
/ 08 февраля 2019

Я смотрю разговор Джейсона Тернера о IIFE.Вот пример, похожий на следующий код:

#include <iostream>
#define EOL '\n'
using std::cout;

class C
{
public:
    C(){ std::cout << "Def ctor\n"; }
    C(const C &c){ std::cout << "Copy ctor\n" << EOL; }
    C(C&& c){ std::cout << "Move ctor\n" << EOL; }
    ~C(){ std::cout << "Dtor\n"; }

    void Print() const { cout << "address: " << this << EOL; }
};
int main()
{
    C c;
    c.Print();
    const auto &refc = [&](){ 
        cout << "lambda returns..." << EOL;
        return c; }();
    refc.Print();
    return 0;
}

Вывод:

Def ctor
address: 0x7ffe6a6765bf
lambda returns...
Copy ctor
address: 0x7ffe6a6765be
Dtor
Dtor

, который показывает, что возвращаемое значение использует конструктор копирования, а возвращаемое значение определяется какконстантная ссылка и создание вновь скопированного объекта для возврата к константной ссылке.

Но если лямбда определена как:

const auto &refc = [&]()->const auto&{ 
    cout << "lambda returns..." << EOL;
    return c; }();

Не вызывается копия ctor, и результат:

Def ctor
address: 0x7fff319dc2af
lambda returns...
address: 0x7fff319dc2af
Dtor

Я думаю, что копия не нужна, есть ли веская причина для дизайна?И мне интересно, что в какой ситуации полезно копирование захваченной переменной?

1 Ответ

0 голосов
/ 08 февраля 2019

Документация по лямбда сообщает нам, каков тип возврата лямбды, если заданный тип возвращаемого значения не указан:

Пропущенный возврат в конце-тип: возвращаемый тип замыкания operator() выводится из операторов возврата , как будто для функции, тип возвращаемого значения которой объявлен auto.

Таким образом, это приводит к вызову конструктора копирования.

Если вы хотите предотвратить это, вы можете использовать auto& или const auto& в качестве конечного типа возврата.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...