設計模式之建造者(Builder)模式

目錄

1、什么是建造者Builder模式?

2、建造者Builder模式的利與弊

3、建造者Builder模式的應用場景

4、建造者模式中的指導者(Director)有什么作用?

5、建造者Builder模式與其他模式的關系

小結


1、什么是建造者Builder模式?

Builder模式是一種創建型設計模式,用于將復雜對象的構建過程和表示分離,使得同樣的構建過程可以創建不同的表示。建造者模式又稱為生成器模式,主要用于對復雜對象的構建及初始化,它可以將多個簡單的組件對象按順序一步步組裝起來,最終完成一個復雜的成品對象。與工廠系列模式不同的是,建造者模式的主要目的在于把煩瑣的構建過程從不同對象中抽離出來,使其脫離并獨立于產品類與工廠類,最終實現用同一套標準的制造工序能夠產出不同的產品

在生活中,一個常見的例子是建筑領域的房屋建造。我們可以將房屋的建造過程看作是使用Builder模式來創建房屋對象的過程。

假設我們需要建造一座房子,房子由多個組成部分(例如地基、樓層、墻壁、窗戶等)組成,并且每個部分都有多個屬性(例如地基的深度、樓層的高度、墻壁的材料等)。

使用Builder模式,我們可以定義一個HouseBuilder類作為建造者,它負責創建和組裝房子的各個部分。HouseBuilder類可以有一些方法來設置房子的各個屬性,例如setFoundationDepth(int depth)、setFloorHeight(int height)等。

另外,我們還可以定義一個House類作為最終構建的產品。House類包含了房子的所有屬性,并提供了訪問這些屬性的方法。

下面是一個簡化的示例代碼:

// 房子類
public class House {private int foundationDepth;private int floorHeight;private String wallMaterial;// 構造函數和訪問方法省略// ...
}// 建造者類
public class HouseBuilder {private House house;public HouseBuilder() {house = new House();}public void setFoundationDepth(int depth) {house.setFoundationDepth(depth);}public void setFloorHeight(int height) {house.setFloorHeight(height);}public void setWallMaterial(String material) {house.setWallMaterial(material);}public House build() {return house;}
}// 使用Builder模式創建房子對象
public class Main {public static void main(String[] args) {HouseBuilder builder = new HouseBuilder();builder.setFoundationDepth(10);builder.setFloorHeight(3);builder.setWallMaterial("Brick");House house = builder.build();// 使用房子對象進行后續操作// ...}
}

在上述示例中,HouseBuilder類負責創建和設置房子的各個屬性,最后通過build()方法返回構建好的House對象。這樣,我們可以根據需要靈活地設置房子的各個部分,并且可以通過調用build()方法來獲取最終的房子對象。

建造者模式的結構圖示:

圖片來源:設計模式-生成器(Builder) - 知乎

?圖片來源:設計模式-生成器(Builder) - 知乎

2、建造者Builder模式的利與弊

Builder模式具有以下優點

  1. 隔離復雜對象的構建過程:Builder模式將復雜對象的構建過程與其表示分離,使得可以獨立地構建不同表示的對象。這樣可以簡化構建過程,提高可讀性和維護性。

  2. 提供靈活的構建方式:通過定義不同的Builder或者使用方法鏈式調用,可以按需設置對象的各個屬性,從而靈活地構建對象。可以根據需要組合不同的屬性,生成不同的對象實例。

  3. 支持構建過程的逐步完善:Builder模式可以支持逐步完善構建過程,即在Builder中逐步添加設置方法,最后調用build方法返回最終的對象。這種方式可以方便地擴展構建過程,適應不同的需求。

  4. 避免構造函數參數過多:當一個類的構造函數參數過多時,使用Builder模式可以避免構造函數的參數列表過長,提高代碼的可讀性。

Builder模式的一些缺點

  1. 增加了類的復雜度:引入了Builder類和多個setter方法,增加了類的復雜度和代碼量。

  2. 對象構建過程的冗余:Builder模式會創建一個Builder對象來構建目標對象,可能會導致額外的對象創建開銷。

  3. 不適用于簡單對象:如果目標對象的屬性較少,構建過程相對簡單,使用Builder模式可能不是最優選擇,會增加代碼量和復雜度。

需要根據具體情況來權衡使用Builder模式的利弊。在復雜對象的構建過程中,特別是當對象具有大量屬性或者構建過程需要逐步完善時,Builder模式可以提供一種靈活、可讀性高的解決方案。

3、建造者Builder模式的應用場景

  1. 構建復雜對象:當需要構建的對象具有多個屬性,并且構建過程較為復雜時,可以考慮使用Builder模式。例如,構建包含大量配置選項的文檔生成器、圖形界面中的復雜組件等。

  2. 避免重疊構造函數:當一個類需要多個構造函數來支持不同的對象初始化方式時,可以使用Builder模式來避免創建過多的重疊構造函數,并提供更清晰的對象構建方法。

  3. 創建不可變對象:當需要創建不可變(Immutable)對象時,Builder模式可以很好地與不可變對象的設計原則結合,通過Builder來設置對象的屬性,最終構建出不可變的對象實例。

  4. 流式接口(Fluent Interface):Builder模式可以用于創建流式接口,使得客戶端代碼可以使用鏈式調用的方式來設置對象的屬性,從而提高代碼的可讀性和簡潔性。

  5. 多個構建過程:當需要支持多種構建過程,或者需要逐步完善構建過程時,Builder模式可以提供一種靈活的解決方案,支持根據不同需求構建不同表示的對象。

總的來說,Builder模式適用于需要構建復雜對象、有多個可選參數或需要逐步完善構建過程的情況。通過使用Builder模式,可以將對象的構建過程分離出來,提高靈活性和可讀性。

4、建造者模式中的指導者(Director)有什么作用?

在建造者模式中,指導者(Director)起到了協調和組織的作用。它負責控制構建過程,按照特定的順序調用建造者的方法來構建對象。

指導者的主要作用有以下幾點:

  1. 定義構建順序:指導者確定了構建過程中各個步驟的順序和調用方式。它知道哪些方法應該在何時被調用,以保證對象的正確構建。

  2. 解耦客戶端與具體構建過程:指導者將構建對象的過程封裝起來,并與具體的建造者解耦。客戶端不需要直接與建造者進行交互,而是通過指導者來完成對象的構建。

  3. 簡化客戶端代碼:指導者隱藏了構建細節,使得客戶端可以更簡潔地調用構建過程。客戶端只需要與指導者進行交互,并傳遞必要的參數,而無需關心具體的構建過程。

指導者的實現原理通常是通過將建造者作為參數進行注入,并在內部調用建造者的方法來完成構建過程。指導者根據具體需求和建造者的能力來決定調用哪些方法以及調用順序。

具體實現上,指導者可以提供一個統一的構建方法,接收建造者作為參數,并按照預定的順序調用建造者的方法來構建對象。也可以根據需要提供一系列的構建方法,每個方法負責調用建造者的特定方法,以完成特定的構建步驟。

通過指導者的存在,客戶端可以更簡單地調用構建方法,而無需關心具體的構建細節和順序,從而實現了構建過程的解耦和簡化。

5、建造者Builder模式與其他模式的關系

該片段引自:Builder

1. 許多設計從使用Factory方法(不那么復雜,通過子類更可定制)開始,并向抽象工廠、原型或生成器(更靈活,但更復雜)發展。
2. Builder專注于逐步構建復雜的對象。抽象工廠專門創建相關對象的族。Abstract Factory會立即返回產品,而Builder允許在獲取產品之前運行一些額外的構造步驟
3. 在創建復雜的復合樹時可以使用Builder,因為可以對其構建步驟進行編程以遞歸工作。
4. 您可以將Builder和Bridge結合起來:director類扮演抽象的角色,而不同的構建器充當實現。
5. 抽象工廠、構建者和原型都可以實現為Singleton。

小結

Builder 模式的關鍵是其中的 Director 對象并不直接返回對象,而是通過分步進行對象的創建。在這里 Director 可以提供一個默認的返回對象的接口(即返回通用的復雜對象的創建,不指定或者特定唯一指定BuildPart中的參數)。

通過使用Builder模式,可以避免在構造函數或者setter方法中傳入大量參數,并且可以更加清晰地組織和管理復雜對象的構建過程。

參考:

精講設計模式-Builder模式-CSDN博客

設計模式-生成器(Builder) - 知乎

大白話建造者模式(Builder Pattern) - 張有路 - 博客園

Builder

設計模式系列3 - builder模式 - 知乎


感謝閱讀,碼字不易,多謝點贊!如有不當之處,歡迎反饋指出,感謝!

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/166125.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/166125.shtml
英文地址,請注明出處:http://en.pswp.cn/news/166125.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

百分點科技入選《2023年央國企數字化升級研究報告》

近日,艾瑞咨詢發布了《2023年央國企數字化升級研究報告》,報告總結了央國企數字化升級的方向和特點,并重點研究了基礎平臺及關鍵技術工具、通用及綜合型應用、重要配套建設等方面。報告指出,數據治理是央國企數字化升級過程中的重…

【鴻蒙應用ArkTS開發系列】- 云開發入門實戰二 實現省市地區三級聯動地址選擇器組件(上)

目錄 概述 云數據庫開發 一、創建云數據庫的對象類型。 二、預置數據(為對象類型添加數據條目)。 三、部署云數據庫 云函數實現業務邏輯 一、創建云函數 二、云函數目錄講解 三、創建resources目錄 四、獲取云端憑據 五、導出之前創建的元數據…

HTML新手入門筆記整理:特殊符號

音標符 音標符 字符 Construct 輸出結果 ?、 a a a? ?′ a a a?n ? a a a? ?&#xff5e; a a a? ??、 O O O? ??′ O O O? ? O O O? ?&#xff5e; O O O? 字符 顯示結果 描述 實體名稱 實體編號 空格 <…

【數據結構】F : 道路建設 (Ver. I)

F : 道路建設 (Ver. I) Description 有N個村莊&#xff0c;編號從1到N&#xff0c;你應該建造一些道路&#xff0c;使每個村莊都可以相互連接。 兩個村A和B是相連的&#xff0c;當且僅當A和B之間有一條道路&#xff0c;或者存在一個村C使得在A和C之間有一條道路&#xff0c;并…

編程實例,隨機抽獎編程

編程實例&#xff0c;隨機抽獎編程 操作步驟&#xff1a; 1、將在本店消費的會員數據導入到抽獎池&#xff0c;可以設定最近多少天內的記錄。 2、點擊 開始隨機抽獎&#xff0c;軟件將從抽獎池隨機抽取9名&#xff0c;并不斷變化&#xff0c;每0.02秒重新隨機抽取9名顯示到屏…

Java 項目中常用注解匯總!! (自整理)

Spring框架的注解 PostMapping("/getDetails") post請求 映射到接口 RequestBody 用來接收HTTP請求體中參數 GetMapping("/getDetails") get請求 映射到接口 RequestParam 用來接收URL中的查詢參數 PutMappi…

7:kotlin 數組 (Arrays)

數組是一種數據結構&#xff0c;它保存固定數量的相同類型或其子類型的值。kotlin中最常見的數組類型是對象類型數組&#xff0c;數組由array類表示。 什么時候使用 當你在kotlin中有特殊的底層需求需要滿足時&#xff0c;可以使用數組。例如&#xff0c;如果你有超出常規應用…

關于js的find的基本用法

Array.prototype.find() 是 JavaScript 的一個數組方法&#xff0c;它被用來在數組中查找一個符合條件的元素。一旦找到第一個符合條件的元素, find() 會立即返回這個元素的值&#xff0c;否則返回 undefined。 以下是 find() 方法的基本語法&#xff1a; arr.find(callback(el…

?LeetCode解法匯總1410. HTML 實體解析器

目錄鏈接&#xff1a; 力扣編程題-解法匯總_分享記錄-CSDN博客 GitHub同步刷題項目&#xff1a; https://github.com/September26/java-algorithms 原題鏈接&#xff1a;力扣&#xff08;LeetCode&#xff09;官網 - 全球極客摯愛的技術成長平臺 描述&#xff1a; 「HTML 實…

利用企業被執行人信息查詢API保障商業交易安全

前言 在當今競爭激烈的商業環境中&#xff0c;企業為了保障商業交易的安全性不斷尋求新的手段。隨著技術的發展&#xff0c;利用企業被執行人信息查詢API已經成為了一種強有力的工具&#xff0c;能夠幫助企業在商業交易中降低風險&#xff0c;提高合作的信任度。 企業被執行人…

如何使用 JavaScript 實現圖片上傳并轉換為 LaTeX 公式

在本教程中&#xff0c;我們將學習如何使用 JavaScript 創建一個上傳圖片的功能&#xff0c;并將所選圖片轉換為 LaTeX 公式。我們將使用 FileReader 對象來讀取圖片并將其轉換為 Base64 格式&#xff0c;然后利用 img2latex API 將其轉換為 LaTeX 公式。 1. HTML 結構 首先&…

SpringMVC日志追蹤筆記整理

新建logback-spring.xml <?xml version"1.0" encoding"UTF-8"?> <configuration><property name"PATH" value"./log/business"></property><appender name"STDOUT" class"ch.qos.logback…

linux進程調度(三)-進程終止

文章目錄 2.3 進程退出的幾種情況2.4 進程終止過程分析2.4.1 exit_notify函數2.4.1.1 forget_original_parent函數2.4.1.1.1 find_child_reaper函數2.4.1.1.2 find_new_reaper函數2.4.1.1.3 reparent_leader函數 2.4.1.2 do_notify_parent函數2.4.1.3 release_task函數 2.4.2 d…

GitHub桌面版

GitHub桌面版 一、GitHub 桌面版二、clone 倉庫三、更新倉庫 一、GitHub 桌面版 二、clone 倉庫 三、更新倉庫

穆桂英掛帥

《穆桂英掛帥》 作家&#xff0f;羅光記 穆桂英掛帥破敵&#xff0c; 威風凜凜立戰場。 鐵甲如云奔雷急&#xff0c; 英姿颯爽傲寒霜。 烽火連天戰鼓擂&#xff0c; 旌旗翻飛壯心驚。 刀光劍影映紅日&#xff0c; 豪情壯志天地驚。 風云變幻戰事急&#xff0c; 英勇穆桂英…

Azure Machine Learning - Azure可視化圖像分類操作實戰

目錄 一、數據準備二、創建自定義視覺資源三、創建新項目四、選擇訓練圖像五、上傳和標記圖像六、訓練分類器七、評估分類器概率閾值 八、管理訓練迭代 在本文中&#xff0c;你將了解如何使用Azure可視化頁面創建圖像分類模型。 生成模型后&#xff0c;可以使用新圖像測試該模型…

溫馨提示!辦理流量卡千萬不要填寫別人的身份證信息,切記!

可以用別人的身份證辦理流量卡嗎&#xff1f;是很多朋友都比較關注的一個問題&#xff0c;在這里明確的告訴大家一下&#xff0c;當然是不可以的。 ?  不管你是在線下營業廳辦理&#xff0c;還是在線上申請&#xff0c;都是需要提供本人的證件信息才能辦理&#xff1a; 1、…

TIDB拓撲結構

TiDB Server&#xff1a;SQL層&#xff0c;負責接受客戶端的連接&#xff0c;執行SQL解析和優化&#xff0c;最終生成分布式執行計劃。TiDB Server為無狀態的&#xff0c;可增加節點負載均衡。 PD (Placement Driver) Server&#xff1a;整個TiDB集群的元信息管理模塊&#xf…

【超詳細】手搓一個微信日記本

&#x1f380; 文章作者&#xff1a;二土電子 &#x1f338; 關注公眾號獲取更多資料&#xff01; &#x1f438; 期待大家一起學習交流&#xff01; 這里對之前的微信記事本小程序進行了重新編寫&#xff0c;增加了更加詳細的步驟描述&#xff0c;將全部圖片都改成了本地圖…

用EasyAVFilter將網絡文件或者本地文件推送RTMP出去的時候發現CPU占用好高,用的也是vcodec copy呀,什么原因?

最近同事在用EasyAVFilter集成在EasyDarwin中做視頻拉流轉推RTMP流的功能的時候&#xff0c;發現怎么做CPU占用都會很高&#xff0c;但是視頻沒有調用轉碼&#xff0c;vcodec用的就是copy&#xff0c;這是什么原因呢&#xff1f; 我們用在線的RTSP流就不會出現這種情況&#x…