設計模式六大原則(二)

依賴倒置原則

依賴倒置的核心是高層模塊不該該依賴低層模塊,兩者都應該依賴其抽象;抽象不該該依賴細節;細節應該依賴抽象。具體一點說:安排一件事給某一我的作,咱們不該該限制是某一種人,好比小孩、青年、老人等,而是限制爲人,這樣作的好處就是若是有不一樣的事情,能夠不一樣的人完成。好比跨欄,就用青年人完成。這個例子中的高層模塊是「事」,依賴的模塊是「人」,底層模塊是「小孩、青年、老人等」,「人」是底層模塊的抽象,固然,「事」也是一個抽象,「跨欄」則是底層模塊的細節。
php

<?php


namespace Factory\ReplaceModel;

/**
 * Class WrongClassYoung
 * @package Factory\ReplaceModel
 */
class WrongClassYoung
{
    /**
     *
     */
    public function run()
    {
        echo 'biu';
    }
}

/**
 * Class WrongClassHurdle
 * @package Factory\ReplaceModel
 */
class WrongClassHurdle
{
    /**
     * @param WrongClassYoung $wrongClassYoung
     */
    public function do(WrongClassYoung $wrongClassYoung)
    {
        $wrongClassYoung->run();
    }
}

$wrongClassYoung = new WrongClassYoung();
$wrongClassHurdle = new WrongClassHurdle();
// 此種方式限制不少,只能作跨欄運動,也只能青年人蔘加。
// 若是須要添加一項運動,則須要從新添加新的類,因爲沒有對類的限制,可能實現方法不一樣,好比,賽跑start(),拔河start(),
// 這就須要咱們知道每一項運動的開始方法,工做量大,且容易混亂
$wrongClassHurdle->do($wrongClassYoung);


// 優化後的類
// 運動員
/**
 * Interface Sportsman
 * @package Factory\ReplaceModel
 */
interface Sportsman
{
    /**
     * @return mixed
     */
    public function start();
}

/**
 * Class YoungSportsman
 * @package Factory\ReplaceModel
 */
class YoungSportsman implements Sportsman
{
    /**
     * @return mixed|void
     */
    public function start()
    {
        echo 'biu';
    }
}

/**
 * Class ChildrenSportsman
 * @package Factory\ReplaceModel
 */
class ChildrenSportsman implements Sportsman
{
    /**
     * @return mixed|void
     */
    public function start()
    {
        echo 'biu biu';
    }
}

/**
 * 運動項目
 * Interface SportEvent
 * @package Factory\ReplaceModel
 */
interface SportEvent
{
    /**
     * @param Sportsman $sportsman
     * @return mixed
     */
    public function do(Sportsman $sportsman);
}

/**
 * 跨欄運動
 * Class HurdleSportEvent
 * @package Factory\ReplaceModel
 */
class HurdleSportEvent implements SportEvent
{
    /**
     * @param Sportsman $sportsman
     * @return mixed|void
     */
    public function do(Sportsman $sportsman)
    {
        $sportsman->start();
    }
}

/**
 * 拔河運動
 * Class TugOfWar
 * @package Factory\ReplaceModel
 */
class TugOfWar implements SportEvent
{
    /**
     * @param Sportsman $sportsman
     * @return mixed|void
     */
    public function do(Sportsman $sportsman)
    {
        $sportsman->start();
    }
}

$tugOfWar = new TugOfWar();

// 青年拔河比賽
$youngSportMan = new YoungSportsman();
$tugOfWar->do($youngSportMan);

// 兒童拔河比賽
$childrenSportsman = new ChildrenSportsman();
$tugOfWar->do($childrenSportsman);

// 優化後的類中,運動員能夠靈活替換,不會改動代碼內部構造,也不會對已有的內容形成影響。
//其中運動項目也能夠再進行優化,優化至項目能夠靈活更換

接口隔離原則

這裏的接口並非「interface」,接口隔離原則的核心是隻用本身須要的接口。好比:咱們吃飯的時候,有套餐,套餐通常會便宜一些,且已經搭配合理。可是若是套餐中有咱們不喜歡的,那麼套餐對咱們而言就是很差的,這個時候咱們就須要單點(隔離),咱們能夠根據本身須要的去自由搭配。接口隔離原則就如同吃飯單點同樣,咱們只獲取本身須要的,不須要的一律不要
優化

迪米特法則

之和直接朋友交流是迪米特法則的核心思想,好比B是A的朋友,C是B的朋友,則A不能直接和C交際。程序中最容易出現這種狀況,爲了方便,直接調用一個絕不相關的類。好比:A(PeopleClass),屬於一個俱樂部(ClubClass),俱樂部老闆(ClubBossClass),當咱們須要獲取A所屬俱樂部老闆的手機號時,極可能會直接調用老闆的類,而跳過俱樂部。但俱樂部老闆和A沒有直接關係的,它們的關係是俱樂部維持的。
spa

<?php


namespace Factory\ReplaceModel;


/**
 * Class ClubClass
 * @package Factory\ReplaceModel
 */
class ClubClass
{
    /**
     * @return ClubBossClass
     */
    public function getBoss()
    {
        return new ClubBossClass();
    }
}

/**
 * Class ClubBossClass
 * @package Factory\ReplaceModel
 */
class ClubBossClass
{
    /**
     * @return string
     */
    public function getPhone()
    {
        return 'phone';
    }
}

/**
 * false
 * Class AFalseClass
 * @package Factory\ReplaceModel
 */
class AFalseClass
{
    /**
     * @param ClubBossClass $clubBossClass
     * @return string
     */
    public function getClubBossPhone(ClubBossClass $clubBossClass)
    {
        return $clubBossClass->getPhone();
    }
}

/**
 * true
 * Class ATrueClass
 * @package Factory\ReplaceModel
 */
class ATrueClass
{
    /**
     * @param ClubClass $clubClass
     * @return string
     */
    public function getClubBossPhone(ClubClass $clubClass)
    {
        return $clubClass->getBoss()->getPhone();
    }
}
相關文章
相關標籤/搜索