摘自 http://blog.csdn.net/tmljs1988/article/details/6081132
C++头文件相互#include时最好是:
(1)在"CA.h"中 #include "CB.h".
(2)在"CB.h"中用类的前向声明: class CA;
(3)最好加上头文件卫士( #ifndef *** #define *** #endif)
示例如下:
(1)"CA.h":
#ifndef HEADER_CA
#define HEADER_CA
#include "CB.h"
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif
---------------
(2)"CB.h":
#ifndef HEADER_CB
#define HEADER_CB
class CA;//这个必须要用,不能只用#include "CA.h",如果只是#include "CA.h"而没有class CA;则会报错.原因如附录[1].
class CB
{
CA* pA;
//CA a;//错误,因为此时还不知道CA的大小,无法分配空间
};
#endif
---------------
(3)"CA.cpp":
#include "CA.h"
----------------------------------
附录:
[1].h的头文件是不能单独被编译的,必须放在.cpp中.编译器在编译.cpp时会将该.cpp中的#include "*.h"中的头文件复制过来.例如在上面的"CA.cpp"中,编译器将#include展开后是:
(1)先将"CA.h"的内容复制过来:
#ifndef HEADER_CA
#define HEADER_CA
#include "CB.h"
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif
(2)再处理(1),当遇到(1)中的 #include "CB.h" 时,将"CB.h"文件的内容再复制过来:
#ifndef HEADER_CA
#define HEADER_CA
//#include "CB.h" //此处被替换
#ifndef HEADER_CB
#define HEADER_CB
class CA;//这个必须要用,不能只用#include "CA.h",如果只是#include "CA.h"而没有class //CA;则会报错.原因如附录[1].
class CB
{
CA* pA;
//CA a;//错误,因为此时还不知道CA的大小,无法分配空间
};
#endif
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif
-----------------------------
从上面代码可知,用class CA;是正确的.
如果把class CA;换成#include "CA.h",则变为:
#ifndef HEADER_CA
#define HEADER_CA
//#include "CB.h" //此处被替换
#ifndef HEADER_CB
#define HEADER_CB
#include "CA.h"//如果不用class CA;
class CB
{
CA* pA;
//CA a;//错误,因为此时还不知道CA的大小,无法分配空间
};
#endif
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif
-----------------------------
编译器再处理时,又发现了#include "CA.h",则再把"CA.h"文件的内容复制过来:
#ifndef HEADER_CA
#define HEADER_CA //-------[1]
//#include "CB.h" //此处被替换
#ifndef HEADER_CB
#define HEADER_CB
//#include "CA.h"//如果不用class CA;
#ifndef HEADER_CA //-------[10]
#define HEADER_CA
#include "CB.h"
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif //-------[100]
class CB
{
CA* pA; //-------[200]
//CA a;//错误,因为此时还不知道CA的大小,无法分配空间
};
#endif
class CA
{
CB* pB;
CB b;//正确,因为此处已经知道CB类的大小,且定义了CB,可以为b分配空间
};
#endif
编译器再分析时,发现[10]处的HEADER_CA 已经被定义(在[1]处),所以不再定义[10]~[100]之间的代码(即绿色的部分).然后在[200]处定义CA a时发现并没有声明CA(没有class CA),所以产生错误.
总之,如果二个头文件相互引用时,最好不是二个都用#include.
当然如果二个头文件中并没有用到另一个头文件中的类时,二个头文件是可以相互#include的(可以像前面那样自己把#include展开分析):
(1)"CA.h":
#ifndef HEADER_CA
#define HEADER_CA
#include "CB.h"
class CA
{
CB* pB;
};
#endif
---------------
(2)"CB.h":
#ifndef HEADER_CB
#define HEADER_CB
#include "CA.h"
class CB
{
CA* pA;
};
#endif
但是,.cpp文件只能#icnlude “CA.h”.如果#icnlude “CB.h”则错误(展开后CA不识别CB),原因可自己分析。