我遇到了以下代码
class ExDer1 : public ExBase
{
public:
friend int Der1Fn()
{
....
}
};
我在这里有点困惑
friend int Der1Fn()
{
//This has an implementation .Why is it a friend then ? since it can access the private/protected variables of the ExDer1 class ?
}
通常情况下,我希望看到以下内容
friend int Der1Fn(); //No implementation. Indicating that the Der1Fn is a method outside this class
这基本上意味着函数int Der1Fn()
将访问类ExDer1的私有变量。然而,这有一个实现。任何人都能解释一下这意味着什么吗?
更新
所以,如果我有以下代码
class ExDer1 : public ExBase
{
public:
friend int Der1Fn()
{
std::cout << "Hello World";
}
};
int main()
{
Der1Fn(); // error C3767: 'Der1Fn': candidate function(s) not accessible
//.....
}
如何调用Der1Fn?
答案 0 :(得分:2)
您可以在类定义中声明友元函数的主体(就像任何类型的函数一样)。
然而,友元函数遵循所执行的每个函数的相同基本规则:在类定义中声明它(在更改时内联,重新编译所有依赖对象等)是一种不好的做法。
您引用了MSDN示例。他们只是举例说明了如何完成范围界定。函数Der1Fn()在全局命名空间中,而不在ExDer1 :: Der1Fn()中。
您的最新帖子:
类Der1Fn()无法访问ExDer1(它不是类的一部分,它是一个外部函数,将其视为静态)。
但是,在Der1Fn()的主体内部,您可以访问ExDer1类型对象的私有成员变量。
答案 1 :(得分:2)
友元函数(或类)也可以在类外部或内部定义。如果你在里面定义它,你应该在正确的范围内提供匹配的声明,或者发生依赖于参数的查找。
以下示例在逻辑上相同:
示例1:
int Der1Fn();
class ExDer1 : public ExBase
{
public:
friend int Der1Fn()
{
....
}
};
示例2(推荐):
int Der1Fn()
{
....
}
class ExDer1 : public ExBase
{
public:
friend int Der1Fn();
};
如何调用Der1Fn?
与this类似。
答案 2 :(得分:1)
如果某个函数需要访问该类的私有成员,但您不应该成为其成员,那么您将使该函数成为朋友。友元函数可以在类内部或外部实现。
如果在类中声明(并定义)仅的友元函数,那么它的作用域就在周围的命名空间中,就像你在那里定义它一样; 但它只能通过依赖于参数的查找(ADL)找到 - 也就是说,只有使用与其中一个类型相同的命名空间调用它才能找到它参数。
在这种情况下,函数没有参数,因此根本找不到 - 这就是为什么你不能从main
或其他任何地方调用它。你需要在类之外以及类中的friend声明中声明函数。
如果它有一个类类型的参数(或在同一名称空间中作用域的其他类型)会更有用;然后在使用该参数类型调用时会找到它:
class ExDer1 : public ExBase
{
public:
friend int Der1Fn(ExDer1 const &)
{
....
}
};
int main()
{
ExDer1 obj;
Der1Fn(obj); // Found by ADL
}
在类中定义朋友对于(通常)仅由ADL访问的运算符重载特别有用。