Builder 模式 —— 建造者模式(又譯成生成器模式)的主要功能是構(gòu)建復(fù)雜的產(chǎn)品,它是將一個(gè)復(fù)雜對(duì)象的構(gòu)建與它的表示分離,使得同樣的構(gòu)建過程可以創(chuàng)建不同的表示。
舉個(gè)例子,打個(gè)生產(chǎn)電腦的比方,這里簡單一點(diǎn),假設(shè)生產(chǎn)電腦只需要 CUP、內(nèi)存和顯卡,現(xiàn)在需要生產(chǎn)宏基和戴爾兩個(gè)品牌的電腦,不用設(shè)計(jì)模式的實(shí)現(xiàn):
Acer.java











































Dell.java











































Client.java







































仔細(xì)觀察一下上面的實(shí)現(xiàn),不難發(fā)現(xiàn),不管是生產(chǎn)何種品牌的筆記本,在實(shí)現(xiàn)的時(shí)候,它們的步驟基本上都是一樣的,都是生產(chǎn)電腦相應(yīng)的部件并添加都電腦里面,在生產(chǎn)不同品牌電腦
的時(shí)候,都會(huì)重復(fù)處理這幾個(gè)步驟,但是明顯的是,這幾個(gè)步驟都是穩(wěn)定的或者說是一樣的,只是每個(gè)步驟的具體實(shí)現(xiàn)不一樣或者說是變化的,如果將這些變化的部分抽取出來,也就是
說如果將處理過程與具體的步驟的實(shí)現(xiàn)分離開來的話,這樣就能夠復(fù)用這些處理過程,而且這樣一來就能很容易的做到在不同品牌電腦之間切換生產(chǎn)。
使用 Builder 模式的實(shí)現(xiàn),如圖:

Product.java































Acer.java
















Dell.java
















Builder.java


























AcerBuilder.java








































DellBuilder.java








































Director.java


























Client.java




































后臺(tái)輸出:




在這里,Acer 類和 Dell 類是空的,如果是這種情況,那么它們可以省略掉,如果 Product 也不是最終想要的,那么它也可以被省略掉,最終剩下的就只有 Director、Builder、
和具體的 Bulider 實(shí)現(xiàn)類。
在這里,Acer 類和 Dell 類是有關(guān)系的兩個(gè)類,它們都是電腦的品牌之一,如果遇到兩個(gè)或多個(gè)沒有太多關(guān)系的類,假設(shè) Acer 類代表電腦,Dell 類代表汽車,很明顯,Acer 類和
Dell 類就不應(yīng)該再有共同的父類,也就是這種情況下,Product 這個(gè)抽象類不存在了,這時(shí)候問題就來了,那么 Builder 接口的規(guī)定的 getFinalResult() 方法的返回值怎么確定呢??
如果它的返回值類型是 Acer,那么 DellBuilder 類就會(huì)有問題,如果它的返回值類型是 Dell,那么 AcerBuilder 類就會(huì)有問題;
很明顯,這是由于類型不能正確匹配引起的,如果是這種情況,可以將 Product 設(shè)計(jì)成標(biāo)識(shí)接口(空接口,接口里面沒有規(guī)定任何行為方法),再讓這些沒有相互關(guān)系的具體產(chǎn)品類
都去實(shí)現(xiàn)這個(gè)接口,那么 Builder 接口里面規(guī)定的 getFinalResult() 方法的返回值類型依然是 Product 類型,這樣一來問題就解決了。