As you can see, the return type is not a template argument or part of the arguments, so you cannot overload or specialize. Sending on assistant is your best option.
#include <type_traits> template<typename Func, typename... Args> void func_impl(Func&& f, Args&&... args, std::true_type) -> decltype(func_impl(std::forward<Args>(args)...)) { } template<typename Func, typename... Args> void func_impl(Func&& f, Args&&... args, std::false_type) -> decltype(func_impl(std::forward<Args>(args)...)) { } template<typename Func, typename... Args> auto func(Func&& f, Args&&... args) -> decltype(func_impl(std::forward<Func>(f), std::forward<Args>(args)...)) { return func_impl(std::forward<Func>(f), std::forward<Args>(args)..., std::is_pointer<decltype(f(std::forward<Args>(args)...))>::type); }
It seems strange to me that I take the function by rvalue reference, but you also omit the forwarding in your original example.
Another possible solution might be the template default argument and overloading. But this will not work well with the argument list.
source share