深入解析Go設計模式之工廠方法模式:Golang中的實作與應用

什麼是工廠方法模式?

工廠方法模式(Factory Method Pattern)是一種創建型設計模式,它透過定義一個介面來建立對象,但將物件的具體實作延遲到子類別中。這意味著,工廠方法模式允許子類決定實例化哪個類,使得程式碼的擴展更加靈活且易於維護。

與簡單工廠模式相比,工廠方法模式不再依賴單一的工廠類,而是透過抽象工廠介面來實現物件的創建。這種模式強調了“對介面編程,而非對實現編程”的設計原則。了解其他的設計模式相關的可以點選查看 軟體工程中的設計模式:解決問題的最佳實踐

工廠方法模式和簡單工廠模式的區別

工廠方法模式和簡單工廠模式都是創建型設計模式,它們的主要差異體現在物件創建的靈活性、擴展性以及設計原則的遵循。下面我們來詳細比較這兩種模式。簡單工廠模式的介紹與範例可以看上一篇博文,深入理解設計模式之簡單工廠模式:在Golang中的實現與應用

1. 類別結構的設計

  • 簡單工廠模式:物件的建立邏輯集中在一個工廠類別中,根據輸入的參數來決定傳回哪種類型的物件。工廠類別負責所有產品的創建。

    • 結構簡單:只有一個工廠類別負責創造不同的產品物件。
    • 建立邏輯集中:所有創建邏輯都集中在一個地方。
  • 工廠方法模式:透過一個抽象的工廠接口,將物件的創建推遲到子類別來實現。每個特定的工廠類別只負責創造某一種類型的產品。

    • 更加靈活:每個特定工廠負責創建特定的產品類型,且支援透過繼承或實作介面進行擴充。
    • 分散創建邏輯:不同的工廠類別各自負責特定產品的創建,創建邏輯分散。

2. 擴充性

  • 簡單工廠模式:如果需要新增新的產品類型,必須修改工廠類別的程式碼,這會違反“開閉原則」(對擴展開放,對修改關閉)。每次添加新產品,都會影響工廠類的實現。

  • 工廠方法模式:符合開閉原則,當新增新的產品類型時,只需建立新的工廠子類和對應的產品類,而不需要修改現有的工廠類或客戶端程式碼。每個工廠子類別獨立負責特定產品的創建。

3. 產品種類

  • 簡單工廠模式:適用於產品種類較少,且創建邏輯不複雜的情況。當產品種類增加時,工廠類可能會變得過於複雜且難以維護。

  • 工廠方法模式:適用於產品種類較多,且需要頻繁擴展或變更產品類型的情況。每個特定工廠類別只處理一種產品的創建,結構更加清晰。

4. 使用場景

  • 簡單工廠模式

    • 使用場景簡單,只有少量產品類型。
    • 適合不頻繁擴充產品類型的項目。
    • 代碼維護成本較低,適用於小型系統。
  • 工廠方法模式

    • 當有大量不同類型的產品需要創建,且創建邏輯較為複雜時使用。
    • 適合產品類型經常變化或需要擴展的項目。
    • 程式碼更具擴展性,適用於大型系統或複雜業務場景。

5. 實現複雜度

  • 簡單工廠模式:實作較為簡單,只需要一個工廠類,根據輸入參數決定要創建哪種產品。

  • 工廠方法模式:實作較為複雜,涉及多個工廠類別和產品類別。需要定義工廠接口,並由不同的工廠子類別來實現特定產品的創建。

總結

  • 簡單工廠模式適用於創造邏輯簡單、產品種類較少、擴展需求較低的場景,優點是實現簡單、使用方便,但隨著產品種類的增加會逐漸變得難以維護。
  • 工廠方法模式適用於需要頻繁擴展產品種類、對系統靈活性要求較高的場景,雖然實現較為複雜,但它提供了更好的擴展性和更清晰的結構,符合物件導向設計的開閉原則。

根據專案的複雜度和擴展需求,開發者可以選擇合適的工廠模式來提高程式碼的可維護性和擴展性。

解決什麼問題?

工廠方法模式解決了以下問題:

  • 解耦:透過引入工廠接口,客戶端程式碼不再直接依賴具體類,提高了程式碼的靈活性。
  • 擴充性:新產品的新增不需要修改現有程式碼,只需建立新的子類和對應的工廠類,符合開閉原則。
  • 統一創建邏輯:所有產品的創建邏輯集中管理在工廠中,方便進行維護和擴展。

何時使用工廠方法模式?

在以下場景中,工廠方法模式是一個理想選擇:

  • 當一個類別無法預測將要建立的物件類型時。
  • 當一個類別希望由其子類別來指定所建立物件的類型。
  • 當需要將物件的建立與其使用解耦時。

工廠方法模式的優缺點

優點

  1. 靈活性高:新類型的產品只需添加新的工廠和產品類,不會影響現有代碼。
  2. 符合開閉原則:可以在不修改現有程式碼的情況下擴充功能。
  3. 清晰的程式碼結構:透過抽象工廠接口,程式碼結構更加清晰,方便管理。

缺點

  1. 增加類別的數量:需要為每種產品和相應的工廠建立新類別,可能導致類別的數量增加,增加系統複雜性。
  2. 簡單場景過於複雜:對於產品種類少的場景,使用工廠方法模式可能顯得過於複雜。

Golang 中工廠方法模式的實現

下面我們透過一個實際的例子來展示如何在Golang 中實現工廠方法模式。假設我們需要創建不同類型的交通工具(如自行車和汽車),每種交通工具都有自己的實現。工廠方法模式使用子類別的方式延遲生成物件到子類別中實作。 Golang中沒有繼承的概念,所以這裡我們使用使用匿名組合來實現

package main import "fmt" // Vehicle 是所有交通工具的介面type Vehicle interface { Drive() string } // Bike 自行車實作了Vehicle 介面type Bike struct{} func (b *Bike) Drive() string { return " Bike is being driven" } // Car 汽車實作了Vehicle 介面type Car struct{} func (c *Car) Drive() string { return "Car is being driven" } // VehicleFactory 是抽象工廠介面type VehicleFactory interface { CreateVehicle() Vehicle } // BikeFactory 是具體的工廠,用於創建自行車type BikeFactory struct{} func (b *BikeFactory) CreateVehicle() Vehicle { return &Bike{} } // CarFactory 是特定的工廠,用於創建汽車type CarFactory struct{} func (c *CarFactory) CreateVehicle() Vehicle { return &Car{} } func main() { // 建立工廠實例var factory VehicleFactory // 使用自行車工廠factory = &BikeVy{} vehicle1 := facFactory // 使用自行車工廠factory = &BikeVy{} vehicle1 := factory. () fmt.Println(vehicle1.Drive()) // 使用汽車工廠factory = &CarFactory{} vehicle2 := factory.CreateVehicle() fmt.Println(vehicle2.Drive()) }

Golang 實作說明

  • 定義了 Vehicle 接口,所有類型的交通工具(BikeCar)都實作了該介面的 Drive() 方法。
  • 創建了 VehicleFactory 抽象工廠接口,並定義了 CreateVehicle() 方法。
  • BikeFactoryCarFactory 分別實現了 VehicleFactory 接口,用於建立對應類型的交通工具。
  • main() 函數中,透過不同的工廠建立交通工具物件並呼叫其 Drive() 方法。

實際開發中的使用注意事項

  1. 工廠介面設計:設計工廠介面時,確保它能夠涵蓋所有需要創建的產品類型。合理的介面設計可以簡化後續的擴充。
  2. 保持程式碼清晰:盡量避免工廠類之間的複雜依賴關係,確保每個工廠的職責單一。
  3. 性能考慮:如果工廠方法的創建邏輯非常複雜,可能會對性能產生影響。在這種情況下,可以考慮使用快取機製或其他最佳化策略。
  4. 文件與範例:在團隊協作時,為工廠方法模式提供充分的文件和範例,以確保團隊成員理解其使用方式。

參考連結

暫無評論

發送評論 編輯評論

|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ°Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
顏文字
Emoji
小恐龍
花!
上一篇
下一篇
Rain ai 招募前蘋果硬體專家 jean didier allegrucci,推動更有效率的ai半導體研發. ??. Portainer docker compose.