C ++ 11 представляет lambdas , что позволяет нам легче реализовывать отложенные вычисления в C ++, поэтому мне интересно, можно ли сделать std :: invoke таким образом?
Согласно cppreference, std :: invoke реализован с:
template <typename F, typename... Args>
decltype(auto) invoke(F&& f, Args&&... args)
noexcept(std::is_nothrow_invocable_v<F, Args...>)
{
return detail::INVOKE(std::forward<F>(f), std::forward<Args>(args)...);
}
Мы можем видеть много идеальной пересылки здесь, и я хочу сделать эту ленивую оценку.Вот моя реализация:
template <typename F, typename... Args>
constexpr auto delay_invoke(F&& f, Args&&... args) {
return [&]() -> decltype(auto) {
return std::invoke(std::forward<F>(f), std::forward<Args>(args)...);
};
}
И он прошел мой тест в wandbox.Так как эта лямбда захватывается по ссылке, я думаю, что в такой ленивой оценке есть проблема с привязкой, поэтому я пробую вторую реализацию с захватом по значению:
template <typename F, typename... Args>
constexpr auto delay_invoke(F&& f, Args&&... args) {
return [=]() mutable -> decltype(auto) {
return std::invoke(static_cast<F&&>(f), static_cast<Args&&>(args)...);
};
}
, и она также прошла мой тест.Я прав?У вас есть хорошая реализация или другое хорошее решение?спасибо!