熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Delphi編程 >> 正文

用Delphi2005學設計模式之簡單工廠篇

2013-11-23 17:29:10  來源: Delphi編程 
工廠模式中又分為簡單工廠模式工廠方法模式和抽象工廠模式 這裡給大家介紹的簡單工廠模式是其中最簡單的一種如果大家支持的話我會繼續貼出工廠方法模式和抽象工廠模式等後續篇要看大家的反應程度哦!
  
  學習設計模式要對面向對象的程序設計有一定的理解特別是多態性 如果能看懂下面的例子就沒問題了呵呵!
  
  //水果類它是一個抽象產品
  TFruit = Class(TObject)
  
  end;
  
  //蘋果類水果類的具體化
  TApple = class(TFruit)
  
  end;
  
  function Factory(): TFruit;
  var
  f:TFruit;
  begin
  //精髓就是這條語句了明明創建了TApple對象
  //卻將他賦值給TFruit類型的變量
  //其實這樣做好處大大的後面就體會到了
  f:=TAppleCreate();
  result:=f;
  end
  
  在例程中我用到了接口 不明白得可以把它當成一個比抽象類還抽象的抽象類說白了把它當成一個類就沒錯 下面開始吧
  
  這是說明
  
  //我們用一個小果園來說明什麼是簡單工廠
  
  //這個果園裡有葡萄蘋果和草莓三種水果
  
  //所有的水果都有生長耕作和收獲三個步驟
  
  //果園的任務就是讓我們得到葡萄蘋果和草莓這三種水果對象
  
  //我們利用得到的對象可以完成水果生長耕作和收獲三個步驟
  
  //果園就是我們所說的簡單工廠(Factory)
  
  //而葡萄蘋果和草莓這三種水果就是工廠裡的產品 (Pruduct)
  
  //完成產品的過程稱之為外部使用者(Produce)
  
  //使用簡單工廠的好處是
  
  //充分利用了多態性
  //不管你種什麼果園返回的對象並不是具體的葡萄蘋果或者草莓
  //而是返回一個他們的抽象對象 水果(IFruit)
  
  //充分利用了封裝性
  //內部產品發生變化時外部使用者不會受到影響
  
  //他的缺點是
  //如果增加了新的產品就必須得修改工廠(Factory)
  
  這是定義簡單工廠的單元文件源代碼
  
  //SimpleFactorypas 定義簡單工廠的單元文件
  
  //代碼如下==========
  
  unit SimpleFactory;
  
  interface
  
  uses
  SysUtils;
  
  type
  
  //水果類它是一個抽象產品
  //僅僅聲明了所有對象共有的接口並不實現他們
  IFruit = interface(IInterface)
  function Grow: string; //生長
  function Harvest: string; //收獲
  function Plant: string;//耕作
  end;
  
  //葡萄類水果類的具體化
  TGrape = class(TInterfacedObject IFruit)
  function Grow: string;
  function Harvest: string;
  function Plant: string;
  end;
  
  //蘋果類水果類的具體化
  TApple = class(TInterfacedObject IFruit)
  function Grow: string;
  function Harvest: string;
  function Plant: string;
  end;
  
  //草莓類水果類的具體化
  TStrawberry = class(TInterfacedObject IFruit)
  function Grow: string;
  function Harvest: string;
  function Plant: string;
  end;
  
  //果園類它就是工廠類負責給出三種水果的實例
  TFruitGardener = class(TObject)
  public
  //注意 class 關鍵字它定義工廠方法 Factory 是一個靜態函數可以直接使用
  //注意返回值他返回的是最抽象的產品 IFruit 水果類
  //注意他有一個參數來告訴工廠創建哪一種水果
  class function Factory(whichFruit:string): IFruit;
  end;
  
  //聲明一個異常這不是重點
  NoThisFruitException = class(Exception)
  end;
  
  implementation
  
  { ********** TGrape ********** }
  
  function TGrapeGrow: string;
  begin
  result:=葡萄正在生長;
  end;
  
  function TGrapeHarvest: string;
  begin
  result:=葡萄可以收獲了;
  end;
  
  function TGrapePlant: string;
  begin
  result:=葡萄已經種好了;
  end;
  
  { ********** TApple ********** }
  
  function TAppleGrow: string;
  begin
  result:=蘋果正在生長;
  end;
  
  function TAppleHarvest: string;
  begin
  result:=蘋果可以收獲了;
  end;
  
  function TApplePlant: string;
  begin
  result:=蘋果已經種好了;
  end;
  
  { ********** TStrawberry ********** }
  
  function TStrawberryGrow: string;
  begin
  result:=草莓正在生長;
  end;
  
  function TStrawberryHarvest: string;
  begin
  result:=草莓可以收獲了;
  end;
  
  function TStrawberryPlant: string;
  begin
  result:=草莓已經種好了;
  end;
  
  { ********** TFruitGardener ********** }
  
  class function TFruitGardenerFactory(whichFruit:string): IFruit;
  begin
  //精髓就是這條語句了 result:= TAppleCreate()
  //不明白趕緊去復習復習什麼是多態性
  if(LowerCase(whichFruit)=apple)then result:=TAppleCreate()
  else if(LowerCase(whichFruit)=grape)then result:=TGrapeCreate()
  else if(LowerCase(whichFruit)=strawberry)then result:=TStrawberryCreate()
  else Raise NoThisFruitExceptionCreate(這種水果還沒有被種植!);
  end;
  
  end
  
  窗體界面
  
  //MainFormpas 窗體文件這裡說明怎樣使用簡單工廠
  
  unit MainForm;
  
  interface
  
  uses
  Windows Messages SysUtils Variants Classes Graphics Controls Forms
  DialogsSimpleFactory StdCtrls;
  
  type
  TForm = class(TForm)
  RadioButton: TRadioButton;
  RadioButton: TRadioButton;
  RadioButton: TRadioButton;
  RadioButton: TRadioButton;
  procedure RadioButtonClick(Sender: TObject);
  procedure RadioButtonClick(Sender: TObject);
  procedure RadioButtonClick(Sender: TObject);
  procedure RadioButtonClick(Sender: TObject);
  public
  procedure Produce(fruitName:string);
  end;
  
  var
  Form: TForm;
  
  implementation
  
  { ********** TForm ********** }
  
  //這就是生產過程
  //IFruit 類型的臨時變量 f 自己知道種的是哪種水果有趣吧
  //想要什麼盡管來種果園大豐收啦!
  procedure TFormProduce(fruitName:string);
  var
  f: IFruit;
  begin
  try
  f:=TFruitGardenerFactory(fruitName);
  ShowMessage(fPlant());
  ShowMessage(fGrow());
  ShowMessage(fHarvest());
  except
  on e:NoThisFruitException do Messagedlg(eMessagemtInformation[mbOK]);
  end;
  end;
  
  {$R *dfm}
  
  procedure TFormRadioButtonClick(Sender: TObject);
  begin
  Produce(apple);
  end;
  
  procedure TFormRadioButtonClick(Sender: TObject);
  begin
  Produce(grape);
  end;
  
  procedure TFormRadioButtonClick(Sender: TObject);
  begin
  Produce(strawberry);
  end;
  
  procedure TFormRadioButtonClick(Sender: TObject);
  begin
  Produce(other);
  end;
  
  end
  
  工廠模式的目的就是把創建對象的責任和使用對象的責任分開工廠負責統一創建具體產品(蘋果葡萄和草莓)然後再把這些產品轉化為他們的抽象產品(水果)返回給外部使用者作為使用者關心的僅僅是抽象產品預留的接口而不關心他們是怎麼創建的這樣即使因為某些原因導致創建產品的過程發生變化也不會影響到外部使用者在一定程度上保證了程序的可維護性
  
  如果把具體產品類(TAppleTFrabeTStrawberry)暴露到外部如果內部的代碼發生了變動外部也會受到影響工廠就失去了他的意義
From:http://tw.wingwit.com/Article/program/Delphi/201311/24659.html
    推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.