redpearl
redpearl

Reputation: 405

How to use forward class declaration in a function with template?

I have two classes. Each has a pointer pointing to the other class. So I have to use forward class declaration in one of them. This method runs well until I need to use a function with template (which I have to write both the declaration and implementation in the header file).

More specifically, my codes are something like the following files. These files got compiled without problems on Windows by MS Visual Studio 2010. But when I compile them on Mac by XCode 4.3.2, I got an error of "Member access into incomplete type 'ClassB'" in file ClassA.h.

Can anyone tell me how to make it compilable on Mac with XCode?

file ClassA.h

#ifndef CLASS_A
#define CLASS_A

//#include "ClassB.h"

class ClassB;

class ClassA
{
public:
    ClassA();
    template <typename T> 
    void funcA(T *t);

    int iNum;
    ClassB *pB;
};    

template <typename T> 
void ClassA::funcA(T *t)
{
    iNum = *(int*)t;
    iNum += pB->iNum;
}

#endif

file ClassA.cpp

#include "ClassA.h"

ClassA::ClassA()
{
    iNum = 1;
}

file ClassB.h

#ifndef CLASS_B
#define CLASS_B

#include "ClassA.h"

class ClassB
{
public:
    ClassB();
    template <typename T> 
    void funcB(T *t);

    int iNum;
    ClassA *pA;
};

template <typename T> 
void ClassB::funcB(T *t)
{
    iNum = *(int*)t;
    iNum -= pA->iNum;
}

#endif

file ClassB.cpp

#include "ClassB.h"

ClassB::ClassB()
{
    iNum = 2;
}

Main file

#include <stdio.h>
#include "ClassA.h"
#include "ClassB.h"

int main(void)
{
    ClassA objA;
    ClassB objB;

    objA.pB = &objB;
    objB.pA = &objA;

    int a = 11;
    int b = 22;
    objA.funcA(&a);
    objB.funcB(&b);

    printf("Class A: %d, %d\n", objA.iNum, objA.pB->iNum);
    printf("Class B: %d, %d\n", objB.iNum, objB.pA->iNum);

    return 0;
}    

Upvotes: 2

Views: 1730

Answers (1)

tomahh
tomahh

Reputation: 13651

You access pB->iNum in your function definition, which is not known from A class since you did not include classB.h.

Foward declaration helps you to define classes, you can then include your header files. Try something like this:

#ifndef CLASS_A
#define CLASS_A

class ClassB;

class ClassA
{
public:
    ClassA();
    template <typename T> 
    void funcA(T *t);

    int iNum;
    ClassB *pB;
};    

#include "ClassB.h"

template <typename T> 
void ClassA::funcA(T *t)
{
    iNum = *(int*)t;
    iNum += pB->iNum;
}

#endif

And do the same in classB.h

Upvotes: 2

Related Questions