Benjy
Benjy

Reputation: 49

Calling class function by a template function

I have two classes with many functions (The functions mustn't be 'static'). I want to call every time to another function by a template function. I have tried to write the template function but I don't know how should I call the template function with the class function I want. I'm attaching a simple code with the problem:

class FirstClass
{
public:
    FirstClass()
    {
        int y = 7;
        y++;
    }
    void FirstFunction(int x)
    {
        x++;
    }
};

class SecondClass
{
public:
    SecondClass()
    {
        int y = 7;
        y++;
    }
    void SecondFunction(int y)
    {
        y--;
    }
    void ThirdFunction(int y)
    {
        y--;
    }
};

template<class OBJECT, void (*FUNCTION)>
void Test(int x)
{
    OBJECT *a = new OBJECT();
    a->FUNCTION();
    delete a;
}

void main()
{
    Test<FirstClass, &FirstClass.FirstFunction>(5);
    Test<SecondClass, &SecondClass.SecondFunction>(5);
    Test<SecondClass, &SecondClass.ThirdFunction>(5);
}

Thanks...

Upvotes: 0

Views: 87

Answers (1)

user2033018
user2033018

Reputation:

A C++ compiler is particularly good at deducing types. Instead of directly specifying the types of the member functions you want to call, why not letting the compiler do that for you instead?

template <typename T>
void Test(void (T::*f)(int), int x)
{
    auto a = new T;
    (a->*f)(x);
    delete a;
}

Note the weird T::* syntax. It says that f is a pointer to a member function that returns void and takes an int. The class f is a member of is T, which will be deduced by the compiler. To actually call the function, you need to use the (even weirder) ->* syntax. Note that, since a member function has to be invoked over an object, you need to create a T.

It doesn't have to be dynamically allocated, though. You could as well have written:

template <typename T>
void Test(void (T::*f)(int), int x)
{
    T a;
    (a.*f)(x);
}

You call function Test like this:

Test(&FirstClass::FirstFunction, 42);

Upvotes: 3

Related Questions