組合替代繼承

HeadFirst設(shè)計模式第一章闡述的觀點是多用組合,少用繼承.
我的理解是適當使用繼承的特性,不過度設(shè)計.

繼承可能帶來的負擔

書上用到的例子
描述鴨子這個對象 假設(shè)鴨子都有飛行這個屬性

public class Duck {
    public void fly() {
        System.out.println("鴨子的飛行屬性");
    }
}

鴨子的實際對象野鴨會飛

public class YieldDuck extends Duck {
    public void fly() {
        System.out.println("野鴨會飛");
    }
}

鴨子的實際對象玩具鴨不會飛

public class MachineDuck extends Duck {
    public void fly() {
        System.out.println("玩具鴨不會飛");
    }
}

這樣迭代下來會產(chǎn)生一個問題 需要關(guān)注的屬性太多
每一個派生的鴨子 都需要重寫fly方法來確定飛行這個屬性
如果鴨子有飛行, 游泳,跑步...屬性越多 繼承的負擔就越重

利用組合來避開可能的負擔

把鴨子的飛行抽象成一種行為

public class Duck {

    protected DuckBehavior mBehavior;

    public interface DuckBehavior {
        void fly();
    }

    protected void fly() {
        mBehavior.fly();
    }

}

這樣會不會飛可以分別描述
會飛的行為

public class DuckCanFlyBehavior implements Duck.DuckBehavior{

    @Override
    public void fly() {
        System.out.println("DuckCanFlyBehavior fly");
    }

}

不會飛的行為

public class DuckCantFlyBehavior implements Duck.DuckBehavior{

    @Override
    public void fly() {
        System.out.println("DuckCantFlyBehavior fly");
    }

}

再次描述鴨子的派生鴨子 都只需要動態(tài)指定鴨子的組成行為

public class GreenDuck extends Duck {

    public GreenDuck(DuckBehavior behavior)
    {
        mBehavior = behavior;
    }

}

組合替代繼承之后,鴨子的邏輯更加清晰.
維護者只需要分別維護鴨子和鴨子行為的邏輯

組合和繼承的選擇

組合是has-a關(guān)系,繼承是is-a關(guān)系
未完待續(xù)......

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容