C設(shè)計模式李建忠_第1頁
C設(shè)計模式李建忠_第2頁
C設(shè)計模式李建忠_第3頁
C設(shè)計模式李建忠_第4頁
C設(shè)計模式李建忠_第5頁
已閱讀5頁,還剩239頁未讀 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認(rèn)領(lǐng)

文檔簡介

1、單件模式(Singleton Pattern)動機(Motivation):    在軟件系統(tǒng)中,經(jīng)常有這樣一些特殊的類,必須保證它們在系統(tǒng)中只存在一個實例,才能確保它們的邏輯正確性、以及良好的效率。    如何繞過常規(guī)的構(gòu)造器,提供一種機制來保證一個類只創(chuàng)建一個實例?    這應(yīng)該是類設(shè)計者的責(zé)任,而不是類使用者的責(zé)任。結(jié)構(gòu)圖:        意圖:    保證一個類僅有一個實例,并提供一個訪問它的全局訪

2、問點。                                -<<設(shè)計模式>>GOF生活的例子:          適用性:   (1)當(dāng)類只能有一個實例而且客戶可以從一個眾所周知的訪問點訪問它時。   (2)當(dāng)這個唯一實例應(yīng)

3、該是通過子類化可擴展的,并且客戶應(yīng)該無需更改代碼就能使用一個擴展的實例時。代碼實現(xiàn):(1)單線程Singleton實現(xiàn)       class SingleThread_Singleton            private static SingleThread_Singleton instance = null;    &

4、#160;   private  SingleThread_Singleton()        public static SingleThread_Singleton Instance                    get

5、60;                           if (instance = null)                

6、0;                   instance = new SingleThread_Singleton();                     

7、60;          return instance;                        以上代碼在單線程情況下不會出現(xiàn)任何問題。但是在多線程的情況下卻不是安全的。如兩個線程同時運行到 if (instance =

8、 null)判斷是否被實例化,一個線程判斷為True后,在進行創(chuàng)建 instance = new SingleThread_Singleton();之前,另一個線程也判斷(instance = null),結(jié)果也為True.這樣就就違背了Singleton模式的原則(保證一個類僅有一個實例)。怎樣在多線程情況下實現(xiàn)Singleton?(2)多線程Singleton實現(xiàn): 1    class MultiThread_Singleton 2 

9、60;    3       private  static volatile MultiThread_Singleton instance = null; 4       private static object lockHelper = new object(); 

10、;5       private MultiThread_Singleton()   6       public static MultiThread_Singleton Instance 7        8       &#

11、160;   get 9           10               if (instance = null)11            &

12、#160;  12                   lock (lockHelper)13                   14    

13、60;                  if (instance = null)15                       16  

14、                         instance = new MultiThread_Singleton();17               

15、0;       18                   19               20       

16、0;       return instance;21                    22       23     此程序?qū)Χ嗑€程是安全的,使用了一個輔助對象lockHelper,保證只有一個線程創(chuàng)建

17、實例(如果instance為空,保證只有一個線程instance = new MultiThread_Singleton();創(chuàng)建唯一的一個實例)。(Double Check)請注意一個關(guān)鍵字volatile,如果去掉這個關(guān)鍵字,還是有可能發(fā)生線程不是安全的。volatile 保證嚴(yán)格意義的多線程編譯器在代碼編譯時對指令不進行微調(diào)。(3)靜態(tài)Singleton實現(xiàn)3         class Static_Singleton4   &

18、#160;     5             public static readonly Static_Singleton instance = new Static_Singleton();6             private&

19、#160;Static_Singleton()  7         以上代碼展開等同于1     class Static_Singleton2         3             public static&

20、#160;readonly Static_Singleton instance;4             static Static_Singleton()5             6          &

21、#160;      instance = new Static_Singleton();7             8             private Static_Singleton()  9 &#

22、160;       由此可以看出,完全符合Singleton的原則。優(yōu)點: 簡潔,易懂缺點: 不可以實現(xiàn)帶參數(shù)實例的創(chuàng)建抽象工廠模式(Abstract Factory)常規(guī)的對象創(chuàng)建方法:/創(chuàng)建一個Road對象Road road =new Road();new 的問題:    實現(xiàn)依賴,不能應(yīng)對“具體實例化類型”的變化。解決思路:    封裝變化點-哪里變化,封裝哪里    潛臺詞: 如果沒有變化,當(dāng)然不

23、需要額外的封裝!工廠模式的緣起    變化點在“對象創(chuàng)建”,因此就封裝“對象創(chuàng)建”    面向接口編程-依賴接口,而非依賴實現(xiàn)最簡單的解決方法:1 class RoadFactory2 public static Road CreateRoad()3                   &

24、#160;             4   return new Road();   5 6 7 /創(chuàng)建一個Road對象8 Road road=roadFactory.CreateRoad();創(chuàng)建一系列相互依賴對象的創(chuàng)建工作:假設(shè)一個游戲開場景:我們需要構(gòu)造"道路"、"房屋"、"地道&q

25、uot;,"從林".等等對象工廠方法如下: 1     class RoadFactory 2      3         public static Road CreateRoad() 4          

26、;5             return new Road(); 6          7         public static Building CreateBuilding() 8 

27、60;        9             return new Building();10         11         public static Tu

28、nnel CreateTunnel()12         13             return new Tunnel();14         15        

29、0;public static Jungle CreateJungle()16         17             return new Jungle();18         19    

30、 調(diào)用方式如下: 1         Road road =  RoadFactory.CreateRoad();3         Building building = RoadFactory.CreateBuilding();4         Tunn

31、el tunnel = RoadFactory.CreateTunnel();5         Jungle jungle = RoadFactory.CreateJungle();如上可見簡單工廠的問題:    不能應(yīng)對"不同系列對象"的變化。比如有不同風(fēng)格的場景-對應(yīng)不同風(fēng)格的道路,房屋、地道.如何解決:    使用面向?qū)ο蟮募夹g(shù)來"封裝"變

32、化點。動機(Motivate):    在軟件系統(tǒng)中,經(jīng)常面臨著"一系統(tǒng)相互依賴的對象"的創(chuàng)建工作:同時,由于需求的變化,往往存在更多系列對象的創(chuàng)建工作。    如何應(yīng)對這種變化?如何繞過常規(guī)的對象創(chuàng)建方法(new),提供一種"封裝機制"來避免客戶程序和這種"多系列具體對象創(chuàng)建工作"的緊耦合?意圖(Intent):    提供一個創(chuàng)建一系列相關(guān)或相互依賴對象的接口,而無需指定它們具體的類。     

33、;                                            -設(shè)計模式GOF結(jié)構(gòu)圖(Struct):    &

34、#160;       適用性:    1.一個系統(tǒng)要獨立于它的產(chǎn)品的創(chuàng)建、組合和表示時。    2.一個系統(tǒng)要由多個產(chǎn)品系統(tǒng)中的一個來配置時。    3.當(dāng)你要強調(diào)一系列相關(guān)的產(chǎn)品對象的設(shè)計以便進行聯(lián)合使用時。    4.當(dāng)你提供一個產(chǎn)品類庫,而只想顯示它們的接口不是實現(xiàn)時。生活例子:           

35、    結(jié)構(gòu)圖代碼實現(xiàn):1  abstract class AbstractFactory2     3        public abstract AbstractProductA CreateProductA();4        public abstract 

36、AbstractProductB CreateProductB();5     1   abstract class AbstractProductA2     3        public abstract void Interact(AbstractProductB b);4   &

37、#160; 1   abstract class AbstractProductB2     3        public abstract void Interact(AbstractProductA a);4       1    class 

38、Client 2      3         private AbstractProductA AbstractProductA; 4         private AbstractProductB AbstractProductB; 5    

39、     public Client(AbstractFactory factory) 6          7             AbstractProductA = factory.CreateProductA(); 8  

40、60;          AbstractProductB = factory.CreateProductB();            9         10         

41、public void Run()11         12             AbstractProductB.Interact(AbstractProductA);13             AbstractProdu

42、ctA.Interact(AbstractProductB);14         15      1  class ConcreteFactory1:AbstractFactory 2      3         public override&

43、#160;AbstractProductA CreateProductA() 4          5             return new ProductA1(); 6          7 

44、0;       public override AbstractProductB CreateProductB() 8          9             return new ProductB1();10  

45、;       11      1     class ConcreteFactory2:AbstractFactory 2      3         public override AbstractProductA 

46、;CreateProductA() 4          5             return new ProdcutA2(); 6          7      

47、   public override AbstractProductB CreateProductB() 8          9             return new ProductB2();10      &

48、#160;  11     1  class ProductA1:AbstractProductA2     3         public override void Interact(AbstractProductB b)4       

49、60; 5             Console.WriteLine(this.GetType().Name + "interact with" + b.GetType().Name);6         7     1  &#

50、160;class ProductB1:AbstractProductB2     3         public override void Interact(AbstractProductA a)4         5        

51、     Console.WriteLine(this.GetType().Name + "interact with" + a.GetType().Name);6         7     1   class ProdcutA2:AbstractProductA2  

52、0;  3         public override void Interact(AbstractProductB b)4         5             Console.WriteLine(this.GetTy

53、pe().Name + "interact with" + b.GetType().Name);6         7     1  class ProductB2:AbstractProductB2     3        &

54、#160;public override void Interact(AbstractProductA a)4         5             Console.WriteLine(this.GetType().Name + "interact with" + 

55、;a.GetType().Name);6         7      1    public static void Main() 2          3         &#

56、160;/ Abstractfactory1 4             AbstractFactory factory1 = new ConcreteFactory1(); 5             Client c1 = new

57、60;Client(factory1); 6             c1.Run(); 7         / Abstractfactory2 8             AbstractFactory&#

58、160;factory2 = new ConcreteFactory2(); 9             Client c2 = new Client(factory2);10             c2.Run();11   

59、      Abstract Factory注意的幾點:    如果不存在”多系列對象創(chuàng)建“的需求變化,則沒必要應(yīng)用Abstract Factory模式,靜態(tài)工廠方法足矣。    "系列對象"指的是這些對象之間有相互依賴、或作用的關(guān)系。例如游戲開發(fā)場景中的"道路"與"房屋"依賴,“道路”與“地道”的依賴。Abstract Factory模式主要在于應(yīng)對"新系列"的需求變動。其缺點在于難以應(yīng)對”新對

60、象“的需求變動。Abstract Factory模式經(jīng)常和Factory Method模式共同組合來應(yīng)對“對象創(chuàng)建”的需求變化建造者模式(Builder)Builder模式的緣起:    假設(shè)創(chuàng)建游戲中的一個房屋House設(shè)施,該房屋的構(gòu)建由幾部分組成,且各個部分富于變化。如果使用最直觀的設(shè)計方法,每一個房屋部分的變化,都將導(dǎo)致房屋構(gòu)建的重新修正.動機(Motivation):    在軟件系統(tǒng)中,有時候面臨一個"復(fù)雜對象"的創(chuàng)建工作,其通常由各個部分的子對象用一定算法構(gòu)成;由于需求的變化,這個復(fù)雜對象的各個部分經(jīng)

61、常面臨著劇烈的變化,但是將它們組合到一起的算法卻相對穩(wěn)定。    如何應(yīng)對種變化呢?如何提供一種"封裝機制"來隔離出"復(fù)雜對象的各個部分"的變化,從而保持系統(tǒng)中的"穩(wěn)定構(gòu)建算法"不隨需求的改變而改變?意圖(Intent):    將一個復(fù)雜對象的構(gòu)建與其表示相分離,使得同樣的構(gòu)建過程可以創(chuàng)建不同的表示。                   

62、0;                          -設(shè)計模式GOF結(jié)構(gòu)圖(Struct):                   協(xié)作(Collaborations):       &#

63、160;          生活中的例子:             適用性:    1.當(dāng)創(chuàng)建復(fù)雜對象的算法應(yīng)該獨立于該對象的組成部分以及它們的裝配方式時。    2.當(dāng)構(gòu)造過程必須允許被構(gòu)造的對象有不同的表示時。實例代碼:Builder類: 1  public abstract 

64、;class Builder 2      3         public abstract void BuildDoor(); 4         public abstract void BuildWall(); 5   &

65、#160;     public abstract void BuildWindows(); 6         public abstract void BuildFloor(); 7         public abstract void BuildHo

66、useCeiling(); 8      9         public abstract House GetHouse();10     Director類:這一部分是 組合到一起的算法(相對穩(wěn)定)。 1 public class Director 2     &#

67、160;3       public void Construct(Builder builder) 4        5           builder.BuildWall(); 6        

68、60;  builder.BuildHouseCeiling();           7           builder.BuildDoor(); 8           builder.BuildWindows(); 9&

69、#160;          builder.BuildFloor();         10       11     ChineseBuilder類 1    public class ChineseBuilder:

70、Builder 2      3        private House ChineseHouse = new House(); 4         public override void BuildDoor() 5   &#

71、160;      6             Console.WriteLine("this Door 's style of Chinese"); 7          8    

72、;     public override void BuildWall() 9         10             Console.WriteLine("this Wall 's style of Chines

73、e");11         12         public override void BuildWindows()13         14            

74、; Console.WriteLine("this Windows 's style of Chinese");15         16         public override void BuildFloor()17      &#

75、160;  18             Console.WriteLine("this Floor 's style of Chinese");19         20         p

76、ublic override void BuildHouseCeiling()21         22             Console.WriteLine("this Ceiling 's style of Chinese");23  

77、60;      24         public override House GetHouse()25         26             return ChineseHou

78、se;27         28     RomanBuilder類: 1     class RomanBuilder:Builder 2      3         private House Roman

79、House = new House(); 4         public override void BuildDoor() 5          6             Console.Wri

80、teLine("this Door 's style of Roman"); 7          8         public override void BuildWall() 9        

81、; 10             Console.WriteLine("this Wall 's style of Roman");11         12         public o

82、verride void BuildWindows()13         14             Console.WriteLine("this Windows 's style of Roman");15     

83、0;   16         public override void BuildFloor()17         18             Console.WriteLine("this Floor&

84、#160;'s style of Roman");19         20         public override void BuildHouseCeiling()21         22    &#

85、160;        Console.WriteLine("this Ceiling 's style of Roman");23         24         public override House GetHouse

86、()25         26             return RomanHouse;27         28     ChineseBuilder和RomanBuilder這兩個是:這個復(fù)雜對象的兩個部分經(jīng)常面臨著劇烈的

87、變化。 1   public class Client 2      3         public static void Main(string args) 4          5   

88、60;         Director director = new Director(); 6  7             Builder instance; 8  9        

89、     Console.WriteLine("Please Enter House No:");10 11             string No = Console.ReadLine();12 13         

90、60;   string houseType = ConfigurationSettings.AppSettings"No" + No;14 15             instance = (Builder)Assembly.Load("House").CreateInstance("House.&quo

91、t; + houseType);16 17             director.Construct(instance);18 19             House house= instance.GetHouse();20    

92、         house.Show();21 22             Console.ReadLine();23         24     1 <?xml version="1.0

93、" encoding="utf-8" ?>2 <configuration>3   <appSettings>4     <add key="No1" value="RomanBuilder"></add>5     <add key="No2" v

94、alue="ChineseBuilder"></add>6   </appSettings>7 </configuration>Builder模式的幾個要點:Builder模式 主要用于“分步驟構(gòu)建一個復(fù)雜的對象”。在這其中“分步驟”是一個穩(wěn)定的乘法,而復(fù)雜對象的各個部分則經(jīng)常變化。Builder模式主要在于應(yīng)對“復(fù)雜對象各個部分”的頻繁需求變動。其缺點在于難以應(yīng)對“分步驟構(gòu)建算法”的需求變動。Abstract Factory模式解決“系列對象”的需求變化,Builder模式解決“對象部分”的

95、需求變化。Builder械通常和Composite模式組合使用工廠方法模式(Factory Method)耦合關(guān)系:       動機(Motivation):    在軟件系統(tǒng)中,由于需求的變化,"這個對象的具體實現(xiàn)"經(jīng)常面臨著劇烈的變化,但它卻有比較穩(wěn)定的接口。    如何應(yīng)對這種變化呢?提供一種封裝機制來隔離出"這個易變對象"的變化,從而保持系統(tǒng)中"其它依賴的對象"不隨需求的變化而變化。意圖(Intent): 

96、   定義一個用戶創(chuàng)建對象的接口,讓子類決定實例哪一個類。Factory Method使一個類的實例化延遲到子類。                                                     

97、       -設(shè)計模式GOF結(jié)構(gòu)圖(Struct):                生活實例:          適用性:    1.當(dāng)一個類不知道它所必須創(chuàng)建的對象類的時候。    2.當(dāng)一個類希望由它子類來指定它所創(chuàng)建對象的時候。    3.當(dāng)類將創(chuàng)建對象的職責(zé)委托給多個幫助子類中的

98、某個,并且你希望將哪一個幫助子類是代理者這一信息局部化的時候。實例代碼:CarFactory類:1    public abstract class CarFactory2     3        public abstract Car CarCreate();4     Car類: 1  

99、60;public abstract class Car2     3        public abstract void StartUp();4        public abstract void Run();5      

100、60; public abstract void Stop();6       7     HongQiCarFactory類:1   public class HongQiCarFactory:CarFactory2     3        public&

101、#160;override Car CarCreate()4        5            return new HongQiCar();6        7     BMWCarFactory類:1 

102、0; public class BMWCarFactory:CarFactory2     3        public override Car CarCreate()4        5           

103、60;return new BMWCar();6        7     HongQiCar類: 1   public  class HongQiCar:Car 2      3       public override

104、60;void StartUp() 4        5           Console.WriteLine("Test HongQiCar start-up speed!"); 6        7    

105、;   public override void Run() 8        9           Console.WriteLine("The HongQiCar run is very quickly!");10    &

106、#160;  11       public override void Stop()12       13           Console.WriteLine("The slow stop time is 3 second&

107、#160;");14       15     BMWCar類: 1    public  class BMWCar:Car 2      3        public override void Start

108、Up() 4         5            Console.WriteLine("The BMWCar start-up speed is very quickly"); 6        

109、0;7        public override void Run() 8         9            Console.WriteLine("The BMWCar run is quitely 

110、;fast and safe!");10        11        public override void Stop()12        13            C

111、onsole.WriteLine("The slow stop time is 2 second");14        15     app.config1 <?xml version="1.0" encoding="utf-8" ?>2 <configuration>3&

112、#160;  <appSettings>4     <add key="No1" value="HongQiCarFactory"/>5     <add key="No2" value="BMWCarFactory"/>6   </appSettings>7 </

113、configuration>Program類: 1  class Program 2      3         static void Main(string args) 4          5    

114、60;        Console.WriteLine("Please Enter Factory Method No:"); 6             Console.WriteLine("*"); 7       

115、;      Console.WriteLine("no         Factory Method"); 8             Console.WriteLine("1       

116、0;  HongQiCarFactory"); 9             Console.WriteLine("2          BMWCarFactory");10           

117、60; Console.WriteLine("*");11             int no=Int32.Parse(Console.ReadLine().ToString();12             string factoryType=ConfigurationManager

118、.AppSettings"No"+no;13             /CarFactory factory = new HongQiCarFactory();14             CarFactory factory = (CarFacto

119、ry)Assembly.Load("FactoryMehtod").CreateInstance("FactoryMehtod." + factoryType); 15             Car car=factory.CarCreate();16           &#

120、160; car.StartUp();17             car.Run();18             car.Stop();19             20  &

121、#160;      21     Factory Method 模式的幾個要點:Factory Method模式主要用于隔離類對象的使用者和具體類型之間的耦合關(guān)系。面對一個經(jīng)常變化的具體類型,緊耦合關(guān)系會導(dǎo)致軟件的脆弱。Factory Method模式通過面向?qū)ο蟮氖址?,將所要?chuàng)建的具體對象工作延遲到子類,從而實現(xiàn)一種擴展(而非更改)的策略,較好地解決了這種緊耦合關(guān)系。Factory Mehtod模式解決"單個對象"的需求變化,AbstractFactory模式解

122、決"系列對象"的需求變化,Builder模式解決"對象部分"的需求變化原型模式(Prototype)依賴關(guān)系倒置:             動機(Motivate):    在軟件系統(tǒng)中,經(jīng)常面臨著“某些結(jié)構(gòu)復(fù)雜的對象”的創(chuàng)建工作;由于需求的變化,這些對象經(jīng)常面臨著劇烈的變化,但是它們卻擁有比較穩(wěn)定一致的接口。    如何應(yīng)對這種變化?如何向“客戶程序(使用這些對象的程序)"隔離出“這些易變對象”,從而使得

123、“依賴這些易變對象的客戶程序”不隨著需求改變而改變?意圖(Intent):    用原型實例指定創(chuàng)建對象的種類,并且通過拷貝這些原型創(chuàng)建新的對象。                                         -設(shè)計模式GOF結(jié)構(gòu)圖(Struct):  

124、;              生活例子:                                           &#

125、160;            適用性:  1當(dāng)一個系統(tǒng)應(yīng)該獨立于它的產(chǎn)品創(chuàng)建,構(gòu)成和表示時;    2當(dāng)要實例化的類是在運行時刻指定時,例如,通過動態(tài)裝載;    3為了避免創(chuàng)建一個與產(chǎn)品類層次平行的工廠類層次時;    4當(dāng)一個類的實例只能有幾個不同狀態(tài)組合中的一種時。建立相應(yīng)數(shù)目的原型并克隆它們可能比每次用合適的狀態(tài)手工實例化該類更方便一些。 示意性代碼例子:1 publ

126、ic  abstract class NormalActor2     3         public abstract NormalActor clone();4     1    public class NormalActorA:NormalActor2 

127、60;   3        public override NormalActor clone()4        5            Console.WriteLine("NormalActorA is call&quo

128、t;);6            return (NormalActor)this.MemberwiseClone();7            8        9     1   pub

129、lic class NormalActorB :NormalActor2     3        public override NormalActor clone()4        5           

130、0;Console.WriteLine("NormalActorB  was called");6            return (NormalActor)this.MemberwiseClone();7            8     &#

131、160;  9        public class GameSystem           public void Run(NormalActor normalActor)                  NormalActor normalActor

132、1 = normalActor.clone();           NormalActor normalActor2 = normalActor.clone();           NormalActor normalActor3 = normalActor.clone();          

133、 NormalActor normalActor4 = normalActor.clone();           NormalActor normalActor5 = normalActor.clone();                          class Pr

134、ogram                                                 &

135、#160;                                                 &

136、#160;                                                 &

137、#160;                                                        static void Main(string args)          &

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論