3

对于Friend Functions
下的示例 ,以下内容如何成立?

“请注意,无论是在duplicate() 的声明中还是在其后来在main() 中的使用中,我们都没有考虑重复CRectangle 类的成员。它不是!它只是可以访问其私有成员和受保护成员而不是成员。 "

Duplicate 在 CRectangle 的公共部分中声明。它怎么不是成员函数而 set_values 是?

这是一个很好的例子吗?没有的话有更好的吗?

4

4 回答 4

13

帕维尔的回答是对您问题的直接回答,但我想您可能不清楚朋友功能的用途,所以我想举一个常见的例子。

友元函数的一个常见用途是重载流运算符,其中特定运算符需要访问(或通过访问促进)对象的私有成员。IE:

class Rectangle
{
...
    friend ostream &operator<<(ostream &stream, Rectangle r);
private:
    int width;
    int height;
};

friend ostream &operator<<(ostream &stream, Rectangle r)
{
    return (stream << "{" << width << ", " << height << "}");
}

在这种情况下,朋友功能允许我们访问私有数据以进行打印,而无需为数据编写“获取”方法。也许这有助于澄清为什么使用友元函数。

于 2009-09-03T00:40:09.407 回答
11

任何在类中声明或定义的函数friend都不是该类的成员。这只是一个朋友功能。

也就是说,如果在类中也定义了友元函数,它将通过涉及该类的 ADL 查找找到(通常用于重载运算符)。

于 2009-09-03T00:21:20.930 回答
1

答案就在类中函数声明之前的friend关键字中。

朋友CRectangle副本(CRectangle);

友元函数只是一个允许访问类私有成员变量的函数。它不是属于该类的成员函数。

set_values 是该类的成员,因为它没有friend 关键字,并且它的范围在类定义内。方法体是在类定义之外定义的。即该类就像一个前向定义,其实现要遵循(如下)。

通过在方法名称前加上 CRectangle:: 前缀,我们告诉编译器这是在 CRectangle 类范围内声明的 set_values 函数的实现。

DeusAduro 关于朋友在哪里有用的答案是朋友类的一个非常常见的用法。

于 2009-09-03T02:31:00.037 回答
1

好的,我也将对此进行破解。

正如大家所指出的,成员函数的声明和友元函数的语法差异,合理地,就是friend关键字。

这是思考这个问题的一种方法。成员函数有一个隐式参数:指向对象本身的指针。例如。在里面set_values你可以使用成员widthand height,它们将是set_values被调用对象的成员。

另一方面,您不能在内部使用标识符width或单独使用标识符,因为它不是成员函数,因此它没有隐式参数,即它不与任何特定对象相关联。友谊的意思是,它可以访问传递给它的任何对象的私有成员,或者它是其范围内的局部变量。heightduplicate()duplicate()CRectangle

另一点:朋友声明甚至不是真正的函数声明。它只是给编译器的一个注释,如果这个特定的函数被定义过,它将被授予访问这个类的私有成员的权限。

于 2009-09-03T02:47:47.670 回答