tmlen
tmlen

Reputation: 9090

Template argument for function type in C++

Here, Wrapper::set should be able to take any function or function object that matches the int(int) signature, and store it into the std::function. It should work with function pointers, lambdas, objects with operator(), std::bind expressions, etc.

#include <functional>

struct Wrapper {
    using function_type = int(int);

    std::function<function_type> func_;

    template<typename Func> void set(Func func) { func_ = func; }
};

What would be the best form of set so that it works in all cases? I.e. one of

Upvotes: 4

Views: 162

Answers (1)

Barry
Barry

Reputation: 302757

The simplest version:

void set(std::function<function_type> f) {
    func_ = std::move(f);
}

The complex version:

template <class F,
    class = std::enable_if_t<std::is_assignable<std::function<function_type>&, F&&>::value>
    >
void set(F&& f) {
    func_ = std::forward<F>(f);
}

There's no reason to do anything else. Both of these handle every case gracefully and correctly, the simple case has an extra move, which for std::function isn't an expensive operation, so I would strongly prefer the simple version unless you have a compelling, proven performance requirement to need the complex one.

Upvotes: 6

Related Questions