Design Patterns Simplified - Part 3 (Simple Factory)【設計模式簡述--第三部分(簡單工廠)】

来源:http://www.cnblogs.com/caofangsheng/archive/2016/08/05/5741830.html
-Advertisement-
Play Games

原文鏈接:http://www.c-sharpcorner.com/UploadFile/19b1bd/design-patterns-simplified-part3-factory/ Design Patterns Simplified - Part 3 (Simple Factory)【設計模 ...


原文鏈接:http://www.c-sharpcorner.com/UploadFile/19b1bd/design-patterns-simplified-part3-factory/

Design Patterns Simplified - Part 3 (Simple Factory)【設計模式簡述--第三部分(簡單工廠)】

This article explains why and how to use the Simple Factory Design Pattern in software development. 這篇文章解釋了在軟體開發中為什麼使用,以及怎麼使用簡單工廠模式。

I am here to continue the discussion of Design Patterns. Today we will explain another creational design pattern called Simple Factory. 

我在這繼續來討論設計模式。今天我將會解釋另一個創造性的設計模式,也就是簡單工廠模式。

In case you have not had a look at our previous articles, go through the following link:

假設你沒有看我之前的文章,請先回去看,下麵是鏈接:

Before talking about its implementation let's begin with some fundamental questions as in the following.

在討論如何實現簡單工廠模式之前,先看下下麵一些基本的問題:

 

Purpose of the Factory pattern【工廠模式的目的】

I can think of two main objectives of using the Factory pattern. One is to achieve loose coupling between the client and business layer, another is to keep all the code for all the object instantiation logic in one place.

我能想到使用工廠模式的兩個主要的目的。一個是在客戶端和業務層之間達到松耦合,另外一個是確保所有對象的實例化的邏輯代碼都在一個位置。

Purpose of loose coupling【松耦合的目的】

In modern software development where changes in existing systems are frequent and software design is expected to be scalable, not having a loosely-coupled design can create many problems.

在現代軟體開發的過程中,需求的變更是很頻繁的,所以軟體的設計應該是要可擴展性好的,沒有一個松耦合的設計,可能會有很多問題。

For example, in an application with a 3-layer architecture, if object creation logic is at the client side, for any new addition of concrete classes, the developer needs to modify not just the business but the client layer as well. Think about the maintainability and added testing effort.

例如,在一個簡單三層框架的項目中,如果對象的創建是在客戶端,那麼任何新添加的具體的實體類,開發者,不僅需要去修改業務層還有客戶端層。為了考慮可維護性,還需要添加測試的工作。

How about if the client is only aware of the high-level contracts and not about its concreate implementation?

如果客戶端只需要關心和高一層次的關係,而不用關心具體的實現呢?

Yes, you got it right! The client just must pass the type of the object it needs and it will get it using the Factory Pattern.

Enough theory. Now let's talk about implementation.

是的,你是對的!客戶端僅僅只需要傳遞對象需要的類型,剩下的就交給工廠模式去做。理論已經足夠了,現在我們來討論一下,如何實現簡單工廠模式吧。

How to use the Simple Factory Pattern【怎麼樣來使用簡單工廠模式】

Let's try to understand using a simple example.

Assume the client wants to know the on-road price of various brands of cars and have an interface as in the following.

我們使用一個簡單的例子,來理解簡單工廠模式吧。假設客戶想要知道路上各種品牌汽車的價格,提供了下麵一個這樣的介面。

我們創建一個控制台程式,來學習簡單工廠模式:

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication1
{
   public interface ICar
    {
       /// <summary>
       /// 獲取汽車價格
       /// </summary>
       /// <param name="model"></param>
       /// <returns></returns>
       string GetOnRoadPrice(string model);
    }
}

 

We need to create a Factory class now that will sit between the client and business layers and it will provide the required object to the client based on the car brand passed.

我們現在需要去創建一個工廠類,這個工廠類位於客戶端和業務層之間,並基於傳遞的汽車品牌,提供客戶端需要的對象。

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication1
{
   public class CarFactory
    {
       /// <summary>
       /// 獲取汽車對象
       /// </summary>
       /// <param name="carBrand">汽車品牌</param>
       /// <returns></returns>
       public static ICar GetCar(string carBrand)
       {
           if (carBrand.ToLowerInvariant() == "baoma")
           {
               return new BaoMa();
           }
           else if (carBrand.ToLowerInvariant() == "benchi")
           {
               return new BenChi();
           }
           else if (carBrand.ToLowerInvariant() == "aodi")
           {
               return new AoDi();
           }
           else
           {
               return null;
           }
       }
    }
}

 

And here goes the concreate business classes.

這裡接著創建具體的實體類。

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ConsoleApplication1
{
    class AoDi:ICar
    {

        public string GetOnRoadPrice(string model)
        {
            if (model.ToLowerInvariant() == "aodi")
            {
                return "300w 人民幣";
            }
            else
            {
                return "你輸入的汽車品牌找不到,請重新輸入!!!";
            }
        }
    }
}

 

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ConsoleApplication1
{
    class BaoMa:ICar
    {
        public string GetOnRoadPrice(string model)
        {
            if (model.ToLowerInvariant() == "baoma")
            {
                return "200w 人民幣";
            }
            else
            {
                return "你輸入的汽車品牌找不到,請重新輸入!!!";
            }
        }
    }
}

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ConsoleApplication1
{
    class BenChi:ICar
    {
      public  string GetOnRoadPrice(string model)
        {
            if (model.ToLowerInvariant() == "glc")
            {
                return "550w 人民幣";
            }
            else
            {
                return "你輸入的汽車品牌找不到,請重新輸入!!!";
            }
        }
    }
}

Now let's see how the client can use the setup we have created so far.

現在,我們看看客戶端怎麼使用我們目前為止創建的對象。

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            //設置控制台標題欄中顯示的標題
            Console.Title = "簡單工廠模式Demo學習";
            ICar car = null;
            string model = null;

            //賓士車測試
           car= CarFactory.GetCar("BenChi");
           model = "glc";
           Console.WriteLine("賓士系列{0}的汽車,售價為{1}",model,car.GetOnRoadPrice(model));
           Console.ReadKey();
        }
    }
}

 

 

 

 

And here goes the class diagram. 這是類圖:

 

As you can see in the preceding code, the client is getting the required object by just passing the car brand. And then it calls the GetOnRoadPrice method to get the On-road price by passing model name. So just to summarize, using simple factory, we achieved the following. 上面的代碼中你可以看到,客戶端獲取需要的對象,僅僅通過傳遞汽車的品牌就可以了。然後傳遞model name調用GetOnRoadPrice 方法來獲取價格。所以總結一下,使用簡單工廠模式,我們達到了下麵的目的。
  • Loose coupling between client and business layers.【客戶端和業務層之間的松耦合。】

  • Placed object creation logic at common place.【把對象的創建邏輯,放在了一個公共的地方。】

  • Abstracted concreate classes (Maruti, Hyundai) from client.【客戶端的類抽象化】

I hope you have liked this article. I look forward to your comments/suggestions.

我希望你喜歡這篇文章,期待你的評論和建議。

 

 

 
您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 虛擬記憶體按頁劃分,我們可以明確告訴系統:某一個虛擬記憶體頁需要和實際記憶體幀相關聯。這樣一來,該記憶體頁就被換進來了,而且不會被系統換出去。這一行為叫做鎖頁(locking a page)。 一般來講頁的換進換出是透明的,一般程式接觸不到這一層。但是呢,鎖頁可以為我們帶來如下好處: 1、速度:如果你的程式 ...
  • 函數的遞歸調用 遞歸的含義 遞歸其實也只是一種演算法上的描述,不是一種新的語法! 有時候,我們解決問題的時候,會遇到這種情況,當我們把一個大的問題按照某種解決方案分成若幹個小的問題的時候,發現這些小問題的解決方案其實和剛纔大問題的解決方案又是一樣的! 典型的,比如:求階乘! 10! = 10 * 9! ...
  • 最近由於公司慢慢往spark方面開始轉型,本人也開始學習,今後陸續會更新一些spark學習的新的體會,希望能夠和大家一起分享和進步。 Spark是什麼? Apache Spark™ is a fast and general engine for large-scale data processin ...
  • 一、總結 二、Bug描述:Mybatis中parameterType使用 mapper層中使用parameterType="java.lang.Integer"基本類型,代碼報錯: 解決辦法,當入參為基本數據類型的使用,使用_parameter代替基本數據類型,如下: 或者在mapper層的介面中, ...
  • 題意概括:那天以後,你好說歹說,都快煉成三寸不爛之舍之際,小A總算不在擺著死人臉,鼓著死魚眼。有了點恢復的徵兆。可孟子這家伙說的話還是有點道理,那什麼天將降....額,總之,由於賢者法陣未完成,而小A又遲遲不現身,FFF團團長連下七道聖火令追殺你們,最先趕到地,機械化部隊,它們除了智能不高外,可以說 ...
  • Spring AOP 的實現主要有兩種:CGLib與JDK自帶的Proxy。 他們主要的區別是,需要JDKProxy修改的類必須實現介面(因此也只能代理public方法),在創建Proxy時可以使用class.getInterfaces()獲得所有介面併進行代理。 而CGLib不受這個限制可以修改任 ...
  • 三大特性是:封裝,繼承,多態 所謂封裝 就是把客觀事物封裝成抽象的類,並且類可以把自己的數據和方法只讓可信的類或者對象操作,對不可信的進行信息隱藏.封裝是面向對象的特征之一,是對象和類概念的主要特性. 簡單的說,一個類就是一個封裝了數據以及操作這些數據的代碼的邏輯實體。在一個對象內部,某些代碼或某些 ...
  • A集成代碼生成器 [正反雙向(單表、主表、明細表、樹形表,開發利器)+快速構建表單;freemaker模版技術 ,0個代碼不用寫,生成完整的一個模塊,帶頁面、建表sql腳本,處理類,service等完整模塊B 集成阿裡巴巴資料庫連接池druid; 資料庫連接池 阿裡巴巴的 druid。Druid在監 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...