2017-02-15 124 views
0

我有一個關於設計模式書中的抽象工廠模式示例代碼的問題。設計模式 - 抽象工廠 - BombedMazeFactory

這本書提出了一個迷宮遊戲的簡單和部分的例子,其中有連接房間的牆壁和門。

有它具有以下的工廠方法基本MazeFactory類:

class MazeFactory { 
public: 
    MazeFactory(); 

    virtual Maze* MakeMaze() const { return new Maze; } 
    virtual Wall* MakeWall() const { return new Wall; } 
    virtual Room* MakeRoom(int n) const { return new Room(n); } 
    virtual Door* MakeDoor(Room* r1, Room* r2) const { 
     return new Door(r1, r2); 
    } 
} 

作者(S),然後定義MazeFactory的專業化:

class BombedMazeFactory : public MazeFactory { 
    BombedMazeFactory(); 

    virtual Room* MakeWall() const { return new BombedWall; } 
    virtual Door* MakeRoom(int n) const { return new RoomWithABomb(n); } 
}; 

我完全不知道怎麼樣RoomWithABomb應該可以工作,但可以說它創造了一個房間,其中有5%的機會容納一個炸彈,如果你打開一個門,其中包含一個爆炸的房間,你爆炸。

現在讓我們說客戶使用BombedMazeFactory類創建他們的迷宮並創建一些房間。創建的房間類型爲RoomWithABomb *,但工廠返回一個房間*。

爲了實現一些迷宮遊戲邏輯,我假設你需要檢查一個房間是否包含炸彈,但是房間*沒有關於炸彈的知識。我們能夠找出房間是否含有炸彈的唯一方法是將房間*改爲RoomWithABomb *這是不正確的做法嗎?

他們的例子不是很好的想法或者是否有其他方式來處理這種情況?

+0

如果每個房間都有一個Enter()方法,則可以在RoomWithABomb子類中覆蓋此方法,並具有隨機設置炸彈的邏輯。 – dbugger

回答

0

這裏的答案是你不需要知道它是什麼樣的房間。 比方說Room是一種方法enter(),當你進入房間時,它可能會打印出一些東西。這個類看起來是這樣的(因爲我沒那麼熟悉C++,我會做到這一點在Java中,但你的想法):

public class Room { 

    protected int roomNumber; 

    public Room(int n) { 
     roomNumber = n; 
    } 

    public void enter() { 
     System.out.println("You entered room number " + roomNumber); 
    } 

    public void getRoomNumber() { 
     return roomNumber; 
    } 
} 

現在讓我們來想想有炸彈的房間。顯然它是Room的派生物,但它應該打印出像「You exploded」這樣的內容。

public class RoomWithABomb extends Room { 
    public RoomWithABomb(int n) { 
     super(n); 
    } 

    public void enter() { 
     System.out.println("Oh no! There was a bomb in the room! You died"); 
    } 

} 

所以現在我們RoomWithABomb類覆蓋從Room類的行爲(多態性!)。然而,呼叫者不需要確切地知道輸入哪種房間,因爲我們知道每個Room(因此還有每個RoomWithABomb,因爲它繼承自Room)具有enter()方法。

那麼抽象工廠的意圖是什麼?我們想要創建類似的對象,從一個公共的超類或接口繼承的對象,以便其他對象不需要知道如何創建它們。通過這樣做,我們還可以將其他對象從所述接口的具體實現中分離出來(迷宮甚至不知道有一個有炸彈的房間)。

+0

我很滿意這個答案。我想enter()需要一個MazeGame實例來改變遊戲的狀態,這會增加耦合,但我看不到一個好的選擇。 – mrpringle