概述
部分治疗来源于:http://www.cnblogs.com/clever101/archive/2009/10/31/1593533.html http://blog.csdn.net/yunyun1886358/article/details/5672574
当两个类出现相互应用时:比如
#pragma once
#include "B.h"
class A
{
B* pointB;
} //A.h
#pragma once
#include"A.h"
class B
{
A* pointA;
} //B.h
//
此时,会在两个类的头文件出现相互包含头文件,如果没有条件编译命令(#pragma one)对编译器而言,会出现头文件相互包含的死循环,【编译器为了避免循环依赖的问题(比如说A.cpp在进行编译的时候,由于包含了A.h,便进行A.h的编译,但A.h包含了B.h,可是B.h又包含了A.h),编译器在进行A.h的时候,可能对A.h做了记录,假定A.h已编译(但实际没有),然后就进入B.h的编译中,在B.h中,由于A.h 并未被编译,所以出现了无法识别A类的问题,进而编译出错】。当存在条件编译时(#pragma once),先编译A.h, 然后转到B.h ,然后又转到A.h,此时,#pragma once告诉编译器,此文件A.h已经被编译了(实际上并没有),此时也出现了无法识别A类的编译错误。
这是就是前置声明出场了,在头文件中用前置声明替换掉了文件包含!如下:
#pragma once
class B; //此次被替换
class A
{
B* pointB;
} //A.h
#pragma once
#include"A.h"
class B
{
A* pointA;
} //B.h
//
这样,就避免了编译出错,前置声明告诉编译器,B是一个类,注意:此时的B是不完整类型,因为不知道类的具体内容!由于B是一个不完整的类型,重点:::所以在A.h中只能存在B的指针或引用!!!!!!!!!!不能使用B的方法,当然也包括B的析构函数了
对于友元函数的解决方案,参见《c++ primer plus》 p607
class Tv
{
friend void Remote::set_cha(Tv& t, intc);
}
为了避免循环依赖,解决方法是:
class Tv; //forward declaration
class Remote{**************};
class Tv{**************};
注意:此时的Remote类定义中不能存在Tv类的方法(即把内联函数直接写在类中).
但可以把内联函数方法定义在Tv类定义的后面,这样仍然实现了内联函数功能.
比如:
class Tv; //forward declaration
class Remote{**************};
class Tv{**************};
inline bool Remote::volup(Tv& t) {return t.volup()}
如此相似的类型还有很多,可以自行判断
//完
最后
以上就是怡然眼神为你收集整理的关于前置声明的全部内容,希望文章能够帮你解决关于前置声明所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复