Re: [設計] 多用合成,少用繼承

作者: adrianshum (Alien)   2014-03-15 22:50:04
※ 引述《internaltide (internaltide)》之銘言:
: 看了一些設計模式跟物件導向的書,都會提到一個觀念就是
: 多用合成,少用繼承
: 之後,自己在寫程式時有嘗試著多使用合成去取代繼承
: 但是發現被合成物件(物件C、D)要取得合成物件(物件A)的資料時都會很不方便
: EX.
: // 物件A
: class objectA{
[43]
: public objectC; //合成的物件C
: public objectD;
: public function func1(){...}
: public function func2(){...}
: }
: // 繼承物件A的物件B
: class objectB extend objectA{
[43]
: }
: 可能同樣的物件內容B跟C,但實際上當要取得物件A的資料時
: 物件B可以很直覺的直接使用物件A的屬性或間接使用方法來取得資料。
: 但物件C就很麻煩了,變成我可能必須在A Class的建構式中時就要把資料
: 想辦法塞到C物件,搞到後來變成當D物件也需要相同資料時,我又得重複
: 塞相同的資料到物件D。 暈!!
: 後來,我都是直接在物件A設了一個名為shareResources的陣列並宣告為Static,
: 再把所有共用資源都往那個陣列塞。
: 然後,無論合成物件或繼承物件都可以直接取用物件A的資料了。
: 不曉得做法好不好,有沒有大師提供更聰明的方法??
首先,當static 牽連到繼承之類的話題,99% 都不會是正確的做法。
單想想,當你有兩個 A instance, 你所謂 shared resource 放的是
哪個 A 的東西。
然後看來你的認知有一個大問題。當談及 繼承 vs 合成,說的完全
不是你的在說的情況。在說以合成取代繼承是類似長這樣的東西:
class A {...}
class B extends A {.....} // 繼承
class C { // 合成
private A a;
....
}
當然這種情況之下, A 通常會有某種interface, 而 C
也會提供這種 interface 並利用內部的 A instance 來
達成。
可是你在說的是
class A {
private C c;
}
這完全是不相干的話題。
至於你的情況下 C 怎樣用到 A 的東西,這涉及你設計的問題,
很難一概而論。當然最常做的是 C 也存著 A 的 reference 然後
C 經此 ref access 包含著自己的那個 A。但更常見的做法是做
好設計,讓 C 能不需要知道自己是被 A 所包含而單純做好自己的
工作就夠。
Alien

Links booklink

Contact Us: admin [ a t ] ucptt.com