我只是对这段代码在这个简单的例子中做了什么有疑问。我查找了朋友课并了解它们是如何工作的,但我不明白顶部的类声明实际上在做什么(即机器人)。这是否意味着Happy类可以使用Robot对象,但是它们无法访问其私有部分,任何信息都将被欣赏。
#include <stdlib.h>
#include <stdexcept>
template <typename T> // What is this called when included
class Robot; // is there a special name for defining a class in this way
template <typename T>
class Happy
{
friend class Joe<T>;
friend class Robot<Happy<T> >;
// ...
};
答案 0 :(得分:5)
这是前瞻声明。
只是告诉编译器,稍后将定义名为Robot
的类模板,并且它应该期望该定义。
与此同时(即,直到Robot
被正式定义),它允许程序员在代码中引用该类型。在您提供的示例中,有必要将Robot
声明为friend
类的Happy
。 (谁选了这些名字?!)
这是避免循环依赖并最小化编译时间/开销的常见策略。
答案 1 :(得分:0)
它基本上对代码的其余部分说“你可以使用它,但我稍后会声明它”。
如果没有这一行,这段代码将无法编译:
friend class Robot<Happy<T> >;
答案 2 :(得分:0)
它被称为前向声明 - 它基本上对编译器说; &#34;相信我,我将使用我将在稍后定义的课程#34;。但是因为编译器对机器人的成员一无所知,所以你只能在只有指针(或引用)的地方使用它。
这是因为否则您需要在此标题中包含Robot标头,这可能会导致其他循环依赖项。
答案 3 :(得分:0)
这被称为“前瞻性声明”。你告诉编译器“有一个叫Robot
的类。我不解释它的样子,但要注意它存在”。这样,当编译器在Robot
的定义中使用Happy
时,编译器不会抛出“未定义的标识符”错误。但是,您仍然必须在某处包含Robot
的完整定义,否则您最终会遇到链接器错误。
当对象需要引用在.h文件中定义得更远的内容时,或者当两个对象需要相互引用时,通常会看到这种情况。