Specifying a member function as a callback in C++11
c++, c++11, lambda
Solution
Only use `std::function` if you really need polymorphic functions. Otherwise make it a template.
To adapt a member function to a functor use `std::mem_fn` and then `bind` an object to the first argument, the resulting functor can serve as your callback.
Sample:
#include <string>
#include <functional>
template<typename F>
class ClassA
{
public:
ClassA(F f) : _cb(f) {}
private:
F _cb;
};
class ClassB
{
public:
ClassB()
: _obj(std::bind(&ClassB::Juggle, this,
std::placeholders::_1))
{}
bool Juggle(const std::string& arg) {return true;}
private:
ClassA<decltype(std::bind(
std::declval<bool (ClassB::*)(const std::string&)>()
, std::declval<ClassB*>()
, std::placeholders::_1
) ) > _obj;
};
int main()
{
ClassB b;
return 0;
}
This side-steps the cost of function at the cost of being horribly ugly.
Problem
I have the following: ``` typedef std::function<bool (const std::string&)> SomethingCoolCb; class ClassA { public: void OnSomethingCool(const SomethingCoolCb& cb) { _cb = cb; } private: SomethingCoolCb _cb; }; class ClassB { public: ClassB(); bool Juggle(const std::string& arg); private: ClassA _obj; }; ``` and I want to specify the ClassB::Juggle() member function as the callback to ClassB::_obj. Would the proper way to do that in C++11 be (in ClassB's constructor): ``` ClassB::ClassB() { _obj.OnDoSomethingCool( [&](const std::string& arg) -> bool { return Juggle(arg); }); } ``` From what I understand, the compiler will make a std::function object out of the above lambda code. So when the callback gets invoked, it'll call the std::function::operator() member and then it'll invoke ClassB::Juggle() instead of invoking ClassB::Juggle() directly. Unless I'm mistaken about what happens under the covers, that all seems to be a little inefficient. Is there a better way?