Конечно, для указателей на функции нет declval.
Что вы имеете в виду?std::declval
отлично работает с типами указателей на функции:
template<typename F, typename... Args>
using call_t = decltype(std::declval<F>()(std::declval<Args>()...));
В этом примере F
может быть типом указателя на функцию, лямбда-типом или любыми вызываемыми типами.
Вот примериспользования:
template<typename T, typename F>
auto foo() -> call_t<F, T>;
Другой пример использования идиомы обнаружения (реализуемой в C ++ 11):
template<typename F, typename... Args>
using is_callable = is_detected<call_t, F, Args...>;
static_assert(is_callable<void(*)(int), int>::value, "callable")
Обратите внимание, что все это можно заменить на std::invoke_result_t
и std::is_invocable
в C ++ 17.Я бы посоветовал имитировать их, чтобы получить наиболее плавное обновление.