Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

c++ header files including each other mutually

I have two classes both defined in separate header files. Each file has a field that is type of other class. Now I included in header of each file the header of other file, but compiler is generating errors. What am i missing?

like image 554
MegaManX Avatar asked Dec 15 '11 21:12

MegaManX


People also ask

Can you include header files in header files C?

In C language, header files contain the set of predefined standard library functions. You request to use a header file in your program by including it with the C preprocessing directive “#include”. All the header file have a '. h' an extension.

Can header files include each other C++?

You cannot have each class have "a field that is type of other class"; that would be a recursive definition and not only the compiler would not be able to make any sense out of it, it does not even make logical sense.

What happens if we include a header file twice in C?

If a header file happens to be included twice, the compiler will process its contents twice. This is very likely to cause an error, e.g. when the compiler sees the same structure definition twice. Even if it does not, it will certainly waste time. This construct is commonly known as a wrapper #ifndef.

What is header file inclusion in C?

A header file is a file with extension . h which contains C function declarations and macro definitions to be shared between several source files. There are two types of header files: the files that the programmer writes and the files that comes with your compiler.


1 Answers

You cannot have each class have "a field that is type of other class"; that would be a recursive definition and not only the compiler would not be able to make any sense out of it, it does not even make logical sense.

Each class having a field that is type of the other class is the kind of impossibility that you only see in M.C. Escher drawings, or animations thereof, like this one:

 

                                            based on Escher's "Print Gallery" Lithograph, 1956

                 B. de Smit and H. W. Lenstra - Source: escherdroste.math.leidenuniv.nl

                     based on Escher's "Print Gallery" Lithograph, 1956, see Wikipedia

 

One of the two fields will have to be a pointer, so as to break the recursive containment, and avoid the logical impossibility.

Which brings us to the next problem: if class B is to contain an instance of class A, then obviously, A has to be declared before class B, so that A is already known to the compiler when compiling B. But if class A is declared before class B, how can we declare a pointer to B in A? Class B is not known yet at the time that A is compiled! The answer to this is a special construct known as forward declaration which exists precisely in order to accommodate situations like this. A forward declaration of class B looks like this:

class B; 

All it is telling the compiler is that there will be a class called B. It does not tell the compiler anything about the contents of class B, so there is very little we can do with it, but we can do one thing: declare pointers to B.

So, the full solution to the problem looks like this:

file "A.h":

/* This is called a "forward declaration".  We use it to tell the compiler that    the identifier "B" will from now on stand for a class, and this class will be    defined later.  We will not be able to make any use of "B" before it has been    defined, but we will at least be able to declare pointers to it. */ class B;  class A {     /* We cannot have a field of type "B" here, because it has not yet been        defined. However, with the forward declaration we have told the compiler        that "B" is a class, so we can at least have a field which is a pointer         to "B". */     B* pb;  } 

file "B.h":

#include "A.h"  class B {    /* the compiler now knows the size of "A", so we can have a field       of type "A". */    A a; } 
like image 102
Mike Nakis Avatar answered Oct 12 '22 07:10

Mike Nakis