Call a functor with a specific function from an overload set

  • A+


In mathematics-related context, I'd like to define functors working on <cmath> functions. For the purpose of this question, we will be using std::invoke as our functor.

This is ill-formed (live demo):

std::invoke(std::sin, 0.0); 

(g++-8.1) error: no matching function for call to 'invoke(<unresolved overloaded function type>, double)'

Indeed, std::sin is an overload set and the compiler lacks the type information to choose one of those functions.


How could I name a specific function from an overload set? With what could we replace LEFT and RIGHT so that the following is well-formed and does what is expected (say, select double std::sin(double))?

#include <functional> #include <cmath>  int main() {     (void) std::invoke(LEFT std::sin RIGHT, 0.0); } 

If this is not possible, is there a way to define a functor so it is overload-set-aware?


The easiest way I know to do this is to use a lambda to enable overload lookup

std::invoke([](auto val){return std::sin(val);}, 0.0); 

Will allow you to pass any value to invoke and then the lambda body will handle the actual call and overload resolution will come in then.

You can use a macro to abstract the lambda body out of the call to invoke using something like

#define FUNCTORIZE(func) [](auto&&... val) noexcept(noexcept(func(std::forward<decltype(val)>(val)...))) -> decltype(auto) {return func(std::forward<decltype(val)>(val)...);} //... std::invoke(FUNCTORIZE(std::sin), 0.0); 


:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen: