I have a function pointer defined by:
typedef void (*EventFunction)(int nEvent);
Is there a way to handle that function with a specific ins
You can use function pointers to index into the vtable of a given object instance. This is called a member function pointer. Your syntax would need to change to use the ".*" and the "&::" operators:
class A;
class B;
typedef void (B::*EventFunction)(int nEvent)
and then:
class A
{
private:
EventFunction handler;
public:
void SetEvent(EventFunction func) { handler = func; }
void EventOne(B* delegate) { ((*delegate).*handler)(1); } // note: ".*"
};
class B
{
private:
A a;
public:
B() { a.SetEvent(&B::EventFromA); } // note: "&::"
void EventFromA(int nEvent) { /* do stuff */ }
};
Run away from raw C++ function pointers, and use std::function instead.
You can use boost::function if you are using an old compiler such as visual studio 2008 which has no support for C++11.
boost:function
and std::function
are the same thing - they pulled quite a bit of boost stuff into the std library for C++11.
Note: you may want to read the boost function documentation instead of the microsoft one as it's easier to understand
Read about pointers to members. To call a method on the derived class, the method has to be declared in the base class as virtual and overriden in the base class and your pointer should point to the base class method. More about pointers to virtual members.
If you're interfacing with a C library, then you can't use a class member function without using something like boost::bind
. Most C libraries that take a callback function usually also allow you to pass an extra argument of your choosing (usually of type void*
), which you can use to bootstrap your class, as so:
class C
{
public:
int Method1(void) { return 3; }
int Method2(void) { return x; }
int x;
};
// This structure will hold a thunk to
struct CCallback
{
C *obj; // Instance to callback on
int (C::*callback)(void); // Class callback method, taking no arguments and returning int
};
int CBootstrapper(CCallback *pThunk)
{
// Call the thunk
return ((pThunk->obj) ->* (pThunk->callback))( /* args go here */ );
}
void DoIt(C *obj, int (C::*callback)(void))
{
// foobar() is some C library function that takes a function which takes no arguments and returns int, and it also takes a void*, and we can't change it
struct CCallback thunk = {obj, callback};
foobar(&CBootstrapper, &thunk);
}
int main(void)
{
C c;
DoIt(&c, &C::Method1); // Essentially calls foobar() with a callback of C::Method1 on c
DoIt(&c, &C::Method2); // Ditto for C::Method2
}
You mention that boost isn't an option for you, but do you have TR1 available to you?
TR1 offers function, bind, and mem_fn objects based on the boost library, and you may already have it bundled with your compiler. It isn't standard yet, but at least two compilers that I've used recently have had it.
http://en.wikipedia.org/wiki/Technical_Report_1
http://msdn.microsoft.com/en-us/library/bb982702.aspx
It's somewhat unclear what you're trying to accomplish here. what is clear is that function pointers is not the way.
maybe what you're looking for is pointer to method.