文章转自公众号:Coder梁(ID:Coder_LT)
我们知道C++控制对象的私有部分的访问,只能通过公共的接口。这样的设计当然没错,但有的时候也会显得过于严格,产生一些问题。
因此C++提供了另外一种形式的访问权限,叫做友元(friend
)。
友元有三种,分别是友元函数、友元类和友元成员函数。
通过让函数成为类的友元,可以赋予该函数与类成员函数一样的访问权限,也就是说我们可以在友元函数当中访问类的私有成员变量。
在介绍友元函数的使用之前,我们需要先了解为什么需要友元函数。C++ Primer
中给了一个非常不错的例子,在之前运算符重载的例子当中,我们实现了一个类Time
。用来记录时间,假设我们需要重载它的*运算符,能够允许一个时间对象和一个浮点数相乘。
很明显,我们只需要重载运算符*即可:
Time Time::operator*(const double x) {
// todo
}
我们在使用的时候大概是这样:
Time a, b;
a = b * 32.5;
但是这里有一个小问题,我们写成a = b * 32.5
;可以,但如果反过来写成32.5 * b
就不行了。因为对于b * 32.5
来说本质上是b调用了operator
*函数,等价于a = b.opeartor*(32.5)
;。但后者就不行了,要怎么解决呢,只能另外实现一个函数来解决了,这个函数有两个input,分别是double
和Time
类型,返回一个Time
类型。
Time operator*(double m, const Time &t);
但这又有了新的问题,由于这不是一个成员函数,不能直接访问类的私有数据。为了破例让它能够访问,我们需要将它设置成友元。
创建友元的方法很简单,我们只需要在函数签名之前加上关键字friend
。
friend Time operator*(double m, const Time &t);
它有两个含义:
- 它不是成员函数,因此不能使用成员函数运算符来调用
- 它与成员函数的访问权限相同,即可以访问所有
private
和public
数据
由于友元函数不是成员函数,所有我们在实现的时候不需要使用Time::
限定符,也不用在实现当中加上关键字friend
,
函数的实现如下:
Time operator*(double m, const Time &t) {
Time result;
long totalminutes = t.hours * m * 60 + t.minutes * m;
result.hours = totalminutes / 60;
result.minutes = totalminutes % 60;
return result;
}
我们在函数当中直接访问了hours
和minutes
成员变量,因此函数必须是友元函数。
当然我们可以把函数稍微变换一下,就可以不必是友元函数了:
Time operator*(double m, const Time &t) {
return t * m; // 调用了t.operator*(m)
}
在这个函数当中,我们没有显式地访问私有变量,因此可以不必是友元。
到此这篇关于C++友元函数讲解的文章就介绍到这了,更多相关C++友元函数内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!