Подтвердить что ты не робот

Возможно ли вернуть объект типа T по ссылке из лямбда без использования синтаксиса типа возвращаемого типа?

Учитывая следующий фрагмент кода:

struct T {}; 

std::function<T&(T&)> f = [](T& obj) -> T& { return obj; };

Мне было интересно, можно ли вывести правильный тип возвращаемого лямбда (т.е. T&) без использования синтаксиса типа возвращаемого типа.

Очевидно, если я удалю -> T&, тогда произойдет ошибка времени компиляции в том, что выведенный тип будет T.

4b9b3361

Ответ 1

В С++ 14 вы можете использовать [](T& obj) -> decltype(auto) { return obj; }. В этом случае возвращаемый тип f выводится из объявленного типа obj (например, T& в этом случае).

Ответ 2

Нет, но в С++ 14 вы можете использовать auto& как тип trailing-return. Если вы печатаете, вас беспокоит, и обновления компилятора вас совсем не волнуют, тогда это в основном решает вашу проблему.

Ответ 3

В С++ 11 вы можете использовать функцию std:: ref для достижения того, что вы просили:

#include <iostream>
#include <functional>

struct T {
  int mI = 0;
};

int main() {
  std::function<T&(T&)> foo = [](T&t) { return std::ref(t); };

  T tObj;
  T & tRef = foo(tObj);

  tRef.mI = 42;

  std::cout<<tObj.mI<<"\n"; // Returns 42
  std::cout<<tRef.mI<<"\n"; // Returns 42

  return 0;
}

Функция

template<class T>
std::reference_wrapper<T> std::ref(T& t)

возвращает объект reference_wrapper, который в основном является объектом, содержащим указатель. Эта ссылочная оболочка может быть неявно преобразована в соответствующую ссылку, см. cppreference.com

Кроме того, вы можете заменить std::function<T&(T&)> на auto:

auto foo = [] (T& t) { return std::ref(t); };