在軟件系統中,常常面臨着「一系列相互依賴的對象」的建立工做;同時,因爲需求的變化,每每存在更多系列對象的建立工做。ide
如何應對這種變化?如何繞過常規的對象建立方法(new),提供一種「封裝機制」來避免客戶程序和這種「多系列具體對象建立工做」的緊耦合?ui
提供一個接口,讓該接口負責建立一系列「相關或者相互依賴的對象」,無需指定它們具體的類。spa
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;設計
namespace 抽象工廠
{
class Program
{
static void Main(string[] args)
{
Screen screen = null;
Mouse mouse = null;
ComputeShop shop = null;對象
while (true)
{
Console.WriteLine("按下1鍵是購買dell產品,按下2鍵購買sam產品");
int num = int.Parse(Console.ReadLine());
switch (num)
{
case 1: shop = new DellComputeShop(); break;
case 2: shop = new SamComputeShop(); break;
default:
shop = null;
Console.WriteLine("請點擊1鍵或2鍵");
break;
}
if (shop!=null)
{
screen = shop.SellScrenn();
mouse = shop.SellMouse();
string s = screen.ToString();
string m = screen.ToString();接口
Console.WriteLine("你購買了{0}和{1}", s, m);
}
}
}
}遊戲
public abstract class Screen
{
}遊戲開發
public abstract class Mouse
{
}開發
public class DellScreen : Screen
{
public override string ToString()
{
return "戴爾屏幕";
}
}string
public class SamScreen : Screen
{
public override string ToString()
{
return "三星屏幕";
}
}
public class DellMouse : Mouse
{
public override string ToString()
{
return "戴爾鼠標";
}
}
public class SamMouse : Mouse
{
public override string ToString()
{
return "三星鼠標";
}
}
public abstract class ComputeShop
{
public abstract Screen SellScrenn();
public abstract Mouse SellMouse();
}
public class DellComputeShop : ComputeShop
{
public override Screen SellScrenn()
{
return new DellScreen();
}
public override Mouse SellMouse()
{
return new DellMouse();
}
}
public class SamComputeShop : ComputeShop
{
public override Screen SellScrenn()
{
return new SamScreen();
}
public override Mouse SellMouse()
{
return new SamMouse();
}
}
}
抽象工廠將產品對象的建立延遲到它的具體工廠的子類。
一般在運行時刻建立一個具體工廠類的實例,這一具體工廠的建立具備特定實現的產品對象,爲建立不一樣的產品對象,客戶應使用不一樣的具體工廠。
把工廠做爲單件,一個應用中通常每一個產品系列只需一個具體工廠的實例,所以,工廠一般最好實現爲一個單件模式。
建立產品,抽象工廠僅聲明一個建立產品的接口,真正建立產品是由具體工廠類建立的,最一般的一個辦法是爲每個產品定義一個工廠方法,一個具體的工廠將爲每一個產品重定義該工廠方法以指定產品,雖然這樣的實現很簡單,但它要求每一個產品系列都要有一個新的具體工廠子類,即便這些產品系列的差異很小。
一個系統不該當依賴於產品類實例如何被建立、組合和表達的細節,這對於全部形態的工廠模式都是重要的。
這個系統有多於一個的產品族,而系統只消費其中某一產品族。
同屬於同一個產品族的產品是在一塊兒使用的,這一約束必須在系統的設計中體現出來。
系統提供一個產品類的庫,全部的產品以一樣的接口出現,從而使客戶端不依賴於實現。
若是沒有應對「多系列對象構建」的需求變化,則沒有必要使用Abstract Factory模式,這時候使用簡單的靜態工廠徹底能夠。
「 系列對象」指的是這些對象之間有相互依賴、或做用的關係,例如遊戲開發場景中的「道路」與「房屋」的依賴,「道路」與「地道」的依賴。
Abstract Factory模式主要在於應對「新系列」的需求變更。其缺點在於難以應對「新對象」的需求變更。
Abstract Factory模式常常和Factory Method模式共同組合來應對「對象建立」的需求變化。
一家門店,只賣一個系列產品:饅頭(玉米滿頭,高粱饅頭)
簡單工廠
多家門店(分店),但還只賣一個系列產品(饅頭)
工廠方法
多家門店,產品系列豐富:饅頭(同上)+包子(芥菜包子,梅乾菜包子)
抽象工廠
Factory Method模式解決「單個對象」的需求變化,
Abstract Factory 模式解決「系列對象」的需求變化,
Builder模式解決「對象部分」的需求變化。