1. 程式人生 > 實用技巧 >設計模式(建造者模式)

設計模式(建造者模式)

一、 簡介

建造者模式(Builder Pattern)也叫生成器模式,是一種物件構建模式。它可以將複雜物件的建造過程抽象出來(抽象類別),使這個抽象過程的不同實現方法可以構造出不同表現(屬性)的物件。

二、UML 類圖

三、建造者模式的實現

案例:

首先我們來看一個簡單的需求現在需要建房子:

1) 修建過程為打樁、砌牆、封頂。

2) 房子有各種各樣的,比如普通房,高樓,別墅,各種房子的過程雖然一樣,但是要求不要相同的。

3) 請編寫程式,完成需求。

常規實現

1、 構建House 類,包含三個屬性打樁、砌牆、封頂

public class House {
    private
String baise; private String wall; private String roofed; public String getBaise() { return baise; } public void setBaise(String baise) { this.baise = baise; } public String getWall() { return wall; } public void setWall(String wall) {
this.wall = wall; } public String getRoofed() { return roofed; } }

2、定義一個抽象類定義三個抽象方法,分別為:打樁、砌牆、封頂

public abstract class HouseBuilder {

    public abstract void buildBase();

    public abstract void buildWall();

    public abstract void buildRoofed();

    public void buildHouse(){
        
this.buildBase(); this.buildWall(); this.buildRoofed(); } }

3、根據房屋的型別去實現HouseBuilder ,以普通房為例

public class CommonHouse extends HouseBuilder {

    @Override
    public void buildBase() {
        System.out.println("構建地基");
    }

    @Override
    public void buildWall() {
        System.out.println("構建圍牆");
    }

    @Override
    public void buildRoofed() {
        System.out.println("構建屋頂");
    }
}

4、模擬一個客戶端

public class ClientTest {

    public static void main(String[] args) {
        CommonHouse commonHouse = new CommonHouse();
        commonHouse.buildHouse();
    }
}

常規實現比較好理解,但是這種設計方案將產品和產品的建立過程封裝在了一起,我們可以將產品和產品的建立過程解耦。我們通過建造者模式實現:

1、修改HouseBuilder 類,通過build() 方法返回構建好的房子物件

public abstract class HouseBuilder {

    protected House house = new House();

    public abstract void buildBase();
    public abstract void buildWalls();
    public abstract void buildRoofed();

    public House build(){
        return house;
    }
}

2、 定義一個HouseDirector, 將房子的具體建造過程交給constructHouse 方法。

public class HouseDirector {

    HouseBuilder houseBuilder = null;

    public HouseDirector(HouseBuilder houseBuilder) {
        this.houseBuilder = houseBuilder;
    }

    public void setHouseBuilder(HouseBuilder houseBuilder) {
        this.houseBuilder = houseBuilder;
    }

    //建造房子的流程,交給指揮者
    public House constructHouse(){
        houseBuilder.buildBase();
        houseBuilder.buildWalls();
        houseBuilder.buildRoofed();
        return houseBuilder.build();
    }
}

3、模擬一個客戶端

public class ClientTest {

    public static void main(String[] args) {
        CommonHousre commonHousre = new CommonHousre();

        HouseDirector director = new HouseDirector(commonHousre);
        director.constructHouse();
    }
}

總結:

1、客戶端(使用程式)不必知道產品內部組成的細節,將產品本身與產品的建立過程解耦,使得相同的建立過程可以建立不同的產品物件。

2、每一個具體建造者都相對獨立,而與其他的具體建造者無關,因此可以很方便地替換具體建造者或增加新的具體建造者, 使用者使用不同的具體建造者即可得到不同的產品物件。

3、可以更加精細地控制產品的建立過程 。將複雜產品的建立步驟分解在不同的方法中,使得建立過程更加清晰,也更方便使用程式來控制建立過程。

4、增加新的具體建造者無須修改原有類庫的程式碼,指揮者類針對抽象建造者類程式設計,系統擴充套件方便,符合“開閉原則”。

5、建造者模式所建立的產品一般具有較多的共同點,其組成部分相似,如果產品之間的差異性很大,則不適合使用建造者模式,因此其使用範圍受到一定的限制。 6、如果產品的內部變化複雜,可能會導致需要定義很多具體建造者類來實現這種變化,導致系統變得很龐大,因此在這種情況下,要考慮是否選擇建造者模式。

7、抽象工廠模式 VS 建造者模式,抽象工廠模式實現對產品家族的建立,一個產品家族是這樣的一系列產品:具有不同分類維度的產品組合,採用抽象工廠模式不需要關心構建過程,只關心什麼產品由什麼工廠生產即可。而建造者模式則是要求按照指定的藍圖建造產品,它的主要目的是通過組裝零配件而產生一個新產品。