問題的起源:
我在看新版的《C++編程思想》的時候,看到拷貝建構函式章節處大致有這麼一,非常不解:
Class A {
int n; //私人的n
public:
A(const A& a): n(a.n){} //為什麼可以調用a.n,n明明是私人的
}
另外在重載=操作符的時候也有這樣的問題。
後來得到的答案是:private是限定異類之間的訪問,而不是限定同類不同對象的訪問
只有smalltalk是連同類不同對象的訪問都限制的
這樣就清楚明白的回答了為什麼拷貝建構函式可以根據一個對象完整的複製出另一個對象。
但是這樣似乎有點不對勁,這樣也就是說C++中的一個類是他自己的友員,那樣的話
同類的不同對象之間是完全透明的,一個對象可以訪問另一個對象所有的成員,包括
私人的。這樣是不是很不合理?
比如,(下面的例子少兒不易):
class 男子 {
private:
小雞雞 jj;
public:
操作(男子 x);
}
我們定義一個男子的類,男子的特徵之一是有個小雞雞,這個應當是私人的,
不然後果不堪設想。下面我們假定有兩個男子:
男子 a,b;
a.操作(b);
倘若在“操作”的定義中有這麼一句:
男子::操作(男子 x){
x.jj = null;
};
這個似乎不太好,即便兩個人都是男子,怎麼能隨便把人家的小雞雞喀嚓掉呢,
除非是情敵。。。-_-!
所以我比較贊成smalltalk的做法,把私人限定到對象身上,而不是類上。
那麼問題又來了,如果限定到對象上,也就是說傳進來的對象,即使是同類對象,
也不能訪問它的私人成員,那麼拷貝建構函式怎麼實現?
我的想法是:
如果那樣設計的話,就應該這麼理解私人、公有和拷貝構造:
拷貝一個對象的時候,只能基於被拷貝對象公開可見的部分進行新對象的建立。
如果某個私人成員可以通過該對象的某個公開方法取得,則取得並賦值;
若沒有方法獲得某個私人成員,則應當給它賦一個初始值。
以上緣自在水木上的對問題的討論。
另外,還有更進一步的YY,假設有個女子的類,假設男子把女子設為friend類,這樣
似乎也不太好,那女子可以任意訪問男子的所有冬冬。。。所以應該把女子的某個
函數(行為)設為friend,在該行為進行過程中,女子可以訪問男子的所有冬冬,
這樣似乎才比較合理。。。(太e了,不繼續了:p)
轉載是因為講的挺好,不過舉例嘛,呵呵,有點^^^^^^^