什麼是原廠模式?
類比生活中的概念,當我們需要打電話的時候,我們需要一部手機,我們通常會選擇直接去賣手機的實體店買。但在程式設計中,當我們需要調用一個類(PhoneA或PhoneB)的方法的時候,我們往往還要關心他是怎麼new出來的(見程式碼片段1)。這就好比我們自己還要去工廠裡面告訴他們你要怎麼生產出一部我需要的手機。而我們只關心他能不能打電話,你怎麼做的關我屁事。所以這就有了原廠模式。原廠模式其實就是抽象出一個工廠,我需要什麼手機,去哪個工廠買就行了。我不必關心他的製作過程,你只要能生產我要的功能的手機就行。所以我們需要引入簡單工廠,讓我們不用再關心手機怎麼生產的,具體代碼的實現見程式碼片段2
複製代碼 代碼如下:public class Customer
{
public void CallSomeOne(){
PhoneA p1 = new PhoneA();
p1.Call();
}
}
public class PhoneA
{
public void Call(){}
}
public class PhoneB
{
public void Call(){}
}
程式碼片段1 :通常的調用類方法的方式
複製代碼 代碼如下:using System;
namespace Example1
{
public interface IProduct { }
public class PhoneA : IProduct { }
public class PhoneB : IProduct { }
public class Factory
{
public IProduct Create()
{
// 工廠決定到底執行個體化哪個子類。
return new PhonetA ();
}
}
}
using System;
namespace Example1
{
public enum Category
{
A,
}
public static class ProductFactory
{
public static IProduct Create(Category category)
{
switch (category)
{
case Category.A:
return new PhoneA();
case Category.B:
return new PhoneB();
default:
throw new NotSupportedException();
}
}
}
}
程式碼片段2:簡單原廠模式的實現
複製代碼 代碼如下:[TestMethod]
public void Test()
{
Factory factory = new Factory();
IProduct phone = factory.Create();
Assert.AreEqual<Type>(phone.GetType(), typeof(PhoneA));
}
程式碼片段3:對簡單原廠模式的測試
新的問題
其實剛剛也提到了,我們只要一隻能打電話的手機,我就想去實體店買一下,我才不關心是哪個工廠生產的呢~而在簡單工廠中,我們還需要關心是哪個工廠生產的(見程式碼片段3)。所以我們在代碼裡面實現一個實體店,這樣我們就不用關心到底是哪個工廠生產的啦。所以我們需要引入抽象工廠,這樣我們只需要跟實體店打交道,不要再關心要去找什麼工廠拿手機了。具體的實現見程式碼片段4.我們可以利用設定檔實現對工廠的選擇,對產品的選擇,因為本文不想引入其他的概念,這裡就不討論了。複製代碼 代碼如下:namespace Example2
{
/// <summary>
/// 抽象的工廠類型特性描述
/// </summary>
public interface IFactory
{
IProduct Create(); // 每個工廠所需要具有的Factory 方法——建立產品
}
/// <summary>
/// 實體工廠類型
/// </summary>
public class FactoryA : IFactory
{
public IProduct Create()
{
return new PhoneA();
}
}
/// <summary>
/// 實體工廠類型
/// </summary>
public class FactoryB : IFactory
{
public IProduct Create()
{
return new PhoneB();
}
}
}
using System;
using System.Diagnostics;
namespace Example2
{
class Client
{
public void SomeMethod()
{
IFactory factory = new FactoryA(); // 獲得了抽象Factory的同時,與FactoryA產生依賴;
IProduct Phone = factory.Create(); // 後續操作僅以來抽象的IFactory和IProduct完成
// ...
}
private IFactory factory;
public Client(IFactory factory) // 將IFactory通過Setter方式注入
{
if (factory == null) throw new ArgumentNullException("factory");
this.factory = factory;
}
public void AnotherMethod()
{
IProduct Phone = factory.Create();
// ... ...
}
}
}
小結
1、Factory 方法模式注重的是整體對象的建立方法
2、Factory 方法的意圖非常明確,它把類的執行個體化過程延遲到子類,將new()的工作交給工廠 完成。同時,增加一個抽象的工廠定義,解決一系列具有統一通用Factory 方法的實體工廠問題。 在.NET 平台中,我們可以藉助配置、泛型和委託的方法在實現傳統模式目的的同時,獲得工廠類型與客戶程式間更加鬆散的構造過程。