Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Type deduction for std::function

The following code is not going to compile because of not calling a matching std::function constructor at the compile time.

template <typename X, typename Y>
Y invoke(std::function<Y(X)> f, X x) {
    return f(x);
}

int func(char x) {
    return 2 * (x - '0');
}

int main() {
    auto val = invoke(func, '2');
    return 0;
}

But is it possible to provide the same (or similar) functionality as expected in the example above? Is there an elegant way to have a function accepting any Callable:

invoke([](int x) -> int { return x/2; }, 100); //Should return int == 50

bool (*func_ptr)(double) = &someFunction;
invoke(func_ptr, 3.141); //Should return bool

?

like image 856
Olinde Rodriguez Avatar asked Dec 19 '22 08:12

Olinde Rodriguez


1 Answers

#include <functional>
#include <cassert>

template <typename F, typename X>
auto invoke(F&& f, X x) -> decltype(std::forward<F>(f)(x)) {
    return std::forward<F>(f)(x);
}

int func(char x) {
    return 2 * (x - '0');
}

bool someFunction(double) {return false;}

int main() {
    auto val = invoke(func, '2');
    assert(val == 4);
    auto val2 = invoke([](int x) -> int { return x/2; }, 100);
    assert(val2 == 50);
    bool (*func_ptr)(double) = &someFunction;
    bool b = invoke(func_ptr, 3.141);
    return 0;
}

Live sample at http://melpon.org/wandbox/permlink/zpkZI3sn1a76SKM8

like image 186
Ville Voutilainen Avatar answered Jan 03 '23 06:01

Ville Voutilainen