荔园在线

荔园之美,在春之萌芽,在夏之绽放,在秋之收获,在冬之沉淀

[回到开始] [上一篇][下一篇]


发信人: Second (石开), 信区: Program
标  题: C++语言常见问题解答(1-7) 夥伴
发信站: 荔园晨风BBS站 (Wed Sep 19 12:06:45 2001), 转信

===================
■□ 第7节:夥伴
===================

Q23:夥伴(friend)是什麽?

让别的类别或函数能存取到你的类别内部的东西。

夥伴可以是函数或其他类别。类别会对它的夥伴开放存取权限。正常情况下,程式员

会下意识、技术性地控制该类别的夥伴与运作行为(否则当你想更动类别时,还得先

有其他部份的拥有者之同意才行)。

========================================

Q24:「夥伴」违反了封装性吗?

若善用之,反而会「强化」封装性。

我们经常得将一个类别切成两半,当这两半各有不同的案例个数及生命期时。在此情

形之下,它们通常需要直接存取对方的内部(这两半“本来”是在同一个类别里面,

所以你并未“增加”存取资料结构的运作行为个数;你只是在“搬动”这些运作行为

所在之处而已)。最安全的实作方式,就是让这两半互为彼此的「夥伴」。

若你如上述般的使用夥伴,你依然是将私有的东西保持在私有的状态。遇到上述的情

况,如果还呆呆的想避免使用夥伴关系,许多人不是采用公共资料(糟透了!),就

是弄个公共的 get/set 存取运作行为来存取彼此的资料,事实上这些都破坏了封装

性。只有在类别的外面该私有资料「仍有其意义」(以使用者的角度来看)时,开放

出私有资料的存取运作行为才称得上是恰当的做法。多数情况下,「存取运作行为」

就和「公共资料」一样糟糕:它们对私有资料成员只隐其“名”而已,却未隐藏其“

存在”。

同样的,如果将「夥伴函数」做为另一种类别公共存取函数的语法,那就和违反封装

性的成员函数一样破坏了封装。换句话说,物件类别的夥伴及成员都是「封装的界线

」,如同「类别定义」本身一样。

========================================

Q25:夥伴函数的优缺点?

它提供了某种介面设计上的自由。

成员函数和夥伴函数都有同等的存取特权(100% 的权利),主要的差别在於:夥伴

函数用起来像是 "f(x)",而成员函数则是 "x.f()"。因此,夥伴函数可让物件类别

设计者挑选他看得最顺眼的语法,以降低维护成本。

夥伴函数主要的缺点在於:当你想做动态系结(dynamic binding)时,它需要额外

的程式码。想做出「虚拟夥伴」的效果,该夥伴函数应该呼叫个隐藏的(通常是放在

"protected:" 里)虚拟成员函数;像这个样子:"void f(Base& b) { b.do_f();
 }"
。衍生类别会覆盖(override)掉那个隐藏的成员函数("void Derived::do_f()")

,而不是该夥伴函数。

========================================

Q26:「夥伴关系无继承及递移性」是什麽意思?

夥伴关系的特权性无法被继承下来:夥伴的衍生类别不必然还是夥伴(我把你当朋友

,但这不代表我也一定会信任你的孩子)。如果 "Base" 类别宣告了 "f()" 为它的

夥伴,"f()" 并不会自动对由 "Base" 衍生出来的 "Derived" 类别所多出来的部

拥有特殊的存取权力。

夥伴关系的特权无递移性:夥伴类别的夥伴不必然还是原类别的夥伴(朋友的朋友不

一定也是朋友)。譬如,如果 "Fred" 类别宣告了 "Wilma" 类别为它的夥伴,而且

"Wilma" 类别宣告了 "f()" 为它的夥伴,则 "f()" 不见得对 "Fred" 有特殊的
存取
权力。

========================================

Q27:应该替类别宣告个成员函数,还是夥伴函数?

可能的话,用成员函数;必要时,就用夥伴。

有时在语法上来看,夥伴比较好(譬如:在 "Fred" 类别中,夥伴函数可把 "Fred"

弄成是第二个参数,但在成员函数中则一定得放在第一个)。另一个好例子是:二元

中序式算数运算子(譬如:"aComplex + aComplex" 可能应该定义成夥伴而非成员函

数,因为你想让 "aFloat + aComplex" 这种写法也能成立;回想一下:成员函数无

法提升它左侧的参数,因为那样会把引发该成员函数的物件所属之类别给改变掉)。


在其他情况下,请选成员函数而不要用夥伴函数。

--
                            既然热爱生命
                            那么,
                            一切都在意料之中。

※ 来源:·荔园晨风BBS站 bbs.szu.edu.cn·[FROM: 192.168.52.239]


[回到开始] [上一篇][下一篇]

荔园在线首页 友情链接:深圳大学 深大招生 荔园晨风BBS S-Term软件 网络书店