Mail Archives: djgpp/2000/03/14/19:56:08
In article <8am435$j8i$1 AT tron DOT sci DOT fi>, Traveler <traveler AT netti DOT fi> wrote:
>I tried to make a table that can store pointers to any kind of functions
>like the one below.
>void func(void);
>int func2(int,int);
>long func3(int);
>void* table[ ] = {func,func2,func3};
>So, what do I have to do to make a table of varied function pointers ?
You'll have to give the compiler more type information --
uses casts when you invoke the function. Try something like this:
typedef void (*FPTR_V_V)(void); /* ptr to func returning void, no args */
typedef int (*FPTR_I_II)(int, int); /* return int, takes two ints */
typedef long (*FPTR_L_I)(int); /* ptr to func that takes int, returns long */
...
(*(FPTR_I_II)(table[1])(5, 6);
Beyond that, you might reconsider why you want a table of
heterogenous functions. Would function overloading do as well?
void func(void) { ... } // Function A
int func(int x, int y) { ... } // Function B
long func(int x) { ... } // Function C
...
// Calls Function B because two int parameters match its signature
func(5, 6)
A more object-oriented approach might be to use a functor object,
which only exists to give an object handle to a function. Consider
this:
class Action {
public:
virtual long do_it(void) = 0;
};
// In place of void func(void)
class NoArgAction: public Action {
public:
long do_it(void) { func(); return 0; }
private:
void func(void) { /* What func did */ system("cat /dev/null"); }
};
// In place of int func2(int, int)
class IntArgsAction : public Action {
public:
long do_it(void) { return func2(i1, i2); }
IntArgsAction(int x, int y) : i1(x), i2(y) { }
void setArgs(int x, int y) { i1 = x ; i2 = y; }
private:
int i1, i2;
long func2(int x, int y) { /* What func2 did */ return x + y; }
};
// In place of long func3(int)
class IntAction : public Action {
public:
long do_it(void) { return func3(i1); }
IntAction(int x) : i1(x) { }
void setArgs(int x) { i1 = x; }
private:
int i1;
long func3(int x) { /* What func3 did */ return x * 7; }
}
// A lot of setup, but here comes the elegant payoff.
// Functions become objects
NoArgAction func;
IntArgsAction func2(5, 6); // Or set parameters later with setArgs
IntAction func3(0);
// Table of pointers to functors, using base class
Action *table[] = { &func, &func2, &func3 };
int
reactToEvent(int event)
{
// Resolves to derived class because do_it() is virtual
return table[event]->do_it();
};
---------
- Raw text -