Java設計模式——建造者模式(創建型模式)


概述

  建造者模式也稱為生成器模式,是一種對象創建型模式,它可以將復雜對象的建造過程抽象出來(抽象類別),使這個抽象過程的不同實現方法可以構造出不同表現(屬性)的對象。
  建造者模式意在為重疊構造器這種反模式(telescoping constructor anti-pattern)找到一種解決方案,對於重疊構造器反模式,我們經常能看到類似於下列的構造器形式(下述例子來源於《Effective Java》):

public NutritionFacts(int servingSize, int servings) {
    this(servingSize, servings, 0);
}

public NutritionFacts(int servingSize, int servings, int calories) {
    this(servingSize, servings, calories, 0);
}

public NutritionFacts(int servingSize, int servings, int calories, int fat) {
    this(servingSize, servings, calories, fat, 0);
}

public NutritionFacts(int servingSize, int servings, int calories, int fat,
                      int sodium) {
    this(servingSize, servings, calories, fat, sodium, 0);
}

public NutritionFacts(int servingSize, int servings, int calories, int fat,
                      int sodium, int carbohydrate) {
    this.servingSize = servingSize;
    this.servings = servings;
    this.calories = calories;
    this.fat = fat;
    this.sodium = sodium;
    this.carbohydrate = carbohydrate;
}    

  如上所見,這些構造器可能包含了一些我們並不想設置的參數,但是還是不得不為其傳遞值,並且,當參數一多,代碼就會變得難以閱讀,時常出現無法知道某一個值的具體含義,必須仔細對照構造器來查找。伴隨着參數的增多,這種方式的構造器將很快是去控制。
  因此當遇到這種許多構造器參數的時候,可以選用建造者模式。

實現方式

public class NutritionFacts {
    private final int servingSize;
    private final int servings;
    private final int calories;
    private final int fat;
    private final int sodium;
    private final int carbohydrate;

    public static class Builder {
        // 必要參數
        private final int servingSize;
        private final int servings;

        // 可選參數
        private int calories = 0;
        private int fat = 0;
        private int carbohydrate = 0;
        private int sodium = 0;

        public Builder(int servingSize, int servings) {
            this.servingSize = servingSize;
            this.servings = servings;
        }

        public Builder calories(int val) {
            calories = val;
            return this;
        }

        public Builder fat(int val) {
            fat = val;
            return this;
        }

        public Builder carbohydrate(int val) {
            carbohydrate = val;
            return this;
        }

        public Builder sodium(int val) {
            sodium = val;
            return this;
        }

        public NutritionFacts build() {
            return new NutritionFacts(this);
        }
    }

    private NutritionFacts(Builder builder) {
        servingSize = builder.servingSize;
        servings = builder.servings;
        calories = builder.calories;
        fat = builder.fat;
        sodium = builder.sodium;
        carbohydrate = builder.carbohydrate;
    }

    public static void main(String[] args) {
        NutritionFacts cocaCola = new NutritionFacts.Builder(240, 8)
                .calories(100).sodium(35).carbohydrate(27).build();
    }
}

  如上代碼所示,這樣的客戶端代碼容易編寫,並且易於閱讀。對於參數值,可以單獨設置組合,不再需要傳遞不必要的參數值。

適用環境

  • 需要生成的產品對象有復雜的內部結構,這些產品對象通常包含多個成員屬性
  • 構建的過程允許對構建的對象進行不同的表示

具體實例

參考資料


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM