一区二区三区在线-一区二区三区亚洲视频-一区二区三区亚洲-一区二区三区午夜-一区二区三区四区在线视频-一区二区三区四区在线免费观看

服務器之家:專注于服務器技術及軟件下載分享
分類導航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術|正則表達式|C/C++|IOS|C#|Swift|Android|VB|R語言|JavaScript|易語言|vb.net|

服務器之家 - 編程語言 - C# - C#編程中使用設計模式中的原型模式的實例講解

C#編程中使用設計模式中的原型模式的實例講解

2021-11-12 15:19張龍豪 C#

這篇文章主要介紹了C#編程中使用設計模式中的原型模式的實例講解,原型模式創建新對象方便快捷,而且可在運行時根據需要通過克隆來添加和去除他們,也可在程序運行是根據情況來修改類內部的數據,需要的朋友可以參考下

一、引言
在軟件系統中,當創建一個類的實例的過程很昂貴或很復雜,并且我們需要創建多個這樣類的實例時,如果我們用new操作符去創建這樣的類實例,這未免會增加創建類的復雜度和耗費更多的內存空間,因為這樣在內存中分配了多個一樣的類實例對象,然后如果采用工廠模式來創建這樣的系統的話,隨著產品類的不斷增加,導致子類的數量不斷增多,反而增加了系統復雜程度,所以在這里使用工廠模式來封裝類創建過程并不合適,然而原型模式可以很好地解決這個問題,因為每個類實例都是相同的,當我們需要多個相同的類實例時,沒必要每次都使用new運算符去創建相同的類實例對象,此時我們一般思路就是想——只創建一個類實例對象,如果后面需要更多這樣的實例,可以通過對原來對象拷貝一份來完成創建,這樣在內存中不需要創建多個相同的類實例,從而減少內存的消耗和達到類實例的復用。 然而這個思路正是原型模式的實現方式。下面就具體介紹下設計模式中的原型設計模式。

二、原型模式的詳細介紹
我們來看一個入學考試場景實例

基對象(一般為接口,抽象類):考試題(樣卷)

原型模式的復職克隆:根據需要印刷考卷,這里的考卷都是復制考試題樣卷

客戶端:學生答卷,同一套試卷,學生做題不可能一模一樣

類圖:

C#編程中使用設計模式中的原型模式的實例講解

接口:試卷樣例代碼

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
/// <summary>
/// 選答題
/// </summary>
public class SelectTest
{
  private string other;
  public string 你老婆多大
  {
    get
    {
      return this.other;
    }
    set
    {
      this.other = value;
    }
  }
}
/// <summary>
/// 面試題
/// </summary>
public interface Itest
{
  Itest Clone();
 
  string 知道設計模式嗎
  {
    get;
    set;
  }
  string 設計模式有幾種
  {
    get;
    set;
  }
  string 你知道那些
  {
    get;
    set;
  }
  SelectTest 附加題
  {
    get;
    set;
  }
 
  Test Test
  {
    get;
    set;
  }
 
  Test Test1
  {
    get;
    set;
  }
}

 

復制克隆:復印機

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
/// <summary>
 /// 繼承Itest接口
 /// </summary>
 public class Test : Itest
 {
   private string one;
   private string two;
   private string three;
   private SelectTest other=new SelectTest();
   public string 知道設計模式嗎
   {
     get
     {
       return this.one;
     }
     set
     {
       this.one = value;
     }
   }
   public string 設計模式有幾種
   {
     get
     {
       return this.two;
     }
     set
     {
       this.two = value;
     }
   }
   public string 你知道那些
   {
     get
     {
       return this.three;
     }
     set
     {
       this.three = value;
     }
   }
   public SelectTest 附加題
   {
     get
     {
       return this.other;
     }
     set
     {
       this.other = value;
     }
   }
   #region IColorDemo 成員
 
   public Itest Clone()
   {
     //克隆當前類
     return (Itest)this.MemberwiseClone();
   }
   #endregion
 }

客戶端,發卷做題

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
static void Main()
   {
     //印刷試卷
     Itest test = new Test();
     //復制樣本試卷
     Itest test1 = test.Clone();
     
     //考生1
     test.設計模式有幾種 = "23";
     test.附加題.你老婆多大 = "18";
 
     //考生2
     test1.設計模式有幾種 = "24";
     test1.附加題.你老婆多大 = "20";
 
     //顯示考生答卷內容
     Console.WriteLine("test設計模式有幾種:" + test.設計模式有幾種);  //23
     Console.WriteLine("test附加題.你老婆多大:" + test.附加題.你老婆多大);  //20
     Console.WriteLine("test1設計模式有幾種:" + test1.設計模式有幾種);  //24
     Console.WriteLine("test1附加題.你老婆多大:" + test1.附加題.你老婆多大); //20
 
     Console.ReadKey();
   }

注意:這里兩個人答得不一樣,為什么附加題中,老婆年齡都為20?

這里涉及到深拷貝,淺拷貝問題,值類型是放在棧上的,拷貝之后,會自會在站上重新add一個,而class屬于引用類型,拷貝之后,棧上重新分配啦一個指針,可指針卻指向同一個位置的資源。淺拷貝,只拷貝值類型,深拷貝,引用類型也拷貝復制。

解決方案:

?
1
2
3
4
5
6
7
8
9
10
public Itest Clone()
   {
     //克隆當前類
     Itest itst= (Itest)this.MemberwiseClone();
     SelectTest st = new SelectTest();
     st.你老婆多大 = this.other.你老婆多大;
     itst.附加題 = st;
     return itst;
 
   }

使用序列化解決

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
/// <summary>
  /// 選答題
  /// </summary>
  [Serializable]
  public class SelectTest
  {
    private string other;
    public string 你老婆多大
    {
      get
      {
        return this.other;
      }
      set
      {
        this.other = value;
      }
    }
  }
  /// <summary>
  /// 面試題
  /// </summary>
  public interface Itest
  {
    Itest Clone();
 
    string 知道設計模式嗎
    {
      get;
      set;
    }
    string 設計模式有幾種
    {
      get;
      set;
    }
    string 你知道那些
    {
      get;
      set;
    }
    SelectTest 附加題
    {
      get;
      set;
    }
   
  }
 
  /// <summary>
  /// 繼承Itest接口
  /// </summary>
 
  public class Test : Itest
  {
    private string one;
    private string two;
    private string three;
    private SelectTest other=new SelectTest();
    public string 知道設計模式嗎
    {
      get
      {
        return this.one;
      }
      set
      {
        this.one = value;
      }
    }
    public string 設計模式有幾種
    {
      get
      {
        return this.two;
      }
      set
      {
        this.two = value;
      }
    }
    public string 你知道那些
    {
      get
      {
        return this.three;
      }
      set
      {
        this.three = value;
      }
    }
    public SelectTest 附加題
    {
      get
      {
        return this.other;
      }
      set
      {
        this.other = value;
      }
    }
 
    
    public Itest Clone()
    {
      SerializableHelper SerializableHelper = new 原型模式.SerializableHelper();
      string target = SerializableHelper.Serializable(this);
      return SerializableHelper.Derializable<Itest>(target);
 
    }
 
  }
 
 
 public class SerializableHelper
  {
    public string Serializable(object target)
    {
      using (MemoryStream stream = new MemoryStream())
      {
        new BinaryFormatter().Serialize(stream, target);
 
        return Convert.ToBase64String(stream.ToArray());
      }
    }
 
    public object Derializable(string target)
    {
      byte[] targetArray = Convert.FromBase64String(target);
 
      using (MemoryStream stream = new MemoryStream(targetArray))
      {
        return new BinaryFormatter().Deserialize(stream);
      }
    }
 
    public T Derializable<T>(string target)
    {
      return (T)Derializable(target);
    }
  }

這就是對原型模式的運用。介紹完原型模式的實現代碼之后,下面看下原型模式的類圖,通過類圖來理清原型模式實現中類之間的關系。具體類圖如下:

C#編程中使用設計模式中的原型模式的實例講解

 

三、原型模式的優缺點

原型模式的優點有

原型模式向客戶隱藏了創建新實例的復雜性
原型模式允許動態增加或較少產品類。
原型模式簡化了實例的創建結構,工廠方法模式需要有一個與產品類等級結構相同的等級結構,而原型模式不需要這樣。
產品類不需要事先確定產品的等級結構,因為原型模式適用于任何的等級結構

原型模式的缺點有:
每個類必須配備一個克隆方法
配備克隆方法需要對類的功能進行通盤考慮,這對于全新的類不是很難,但對于已有的類不一定很容易,特別當一個類引用不支持串行化的間接對象,或者引用含有循環結構的時候。


四、.NET中原型模式的實現
在.NET中可以很容易地通過實現ICloneable接口(這個接口就是原型,提供克隆方法,相當于與上面代碼中MonkeyKingPrototype抽象類)中Clone()方法來實現原型模式,如果我們想我們自定義的類具有克隆的功能,首先定義類繼承與ICloneable接口并實現Clone方法。在.NET中實現了原型模式的類如下圖所示(圖中只截取了部分,可以用Reflector反編譯工具進行查看):

C#編程中使用設計模式中的原型模式的實例講解

延伸 · 閱讀

精彩推薦
  • C#C#實現XML文件讀取

    C#實現XML文件讀取

    這篇文章主要為大家詳細介紹了C#實現XML文件讀取的相關代碼,具有一定的參考價值,感興趣的小伙伴們可以參考一下...

    Just_for_Myself6702022-02-22
  • C#C# 實現對PPT文檔加密、解密及重置密碼的操作方法

    C# 實現對PPT文檔加密、解密及重置密碼的操作方法

    這篇文章主要介紹了C# 實現對PPT文檔加密、解密及重置密碼的操作方法,非常不錯,具有參考借鑒價值,需要的朋友可以參考下...

    E-iceblue5012022-02-12
  • C#深入解析C#中的交錯數組與隱式類型的數組

    深入解析C#中的交錯數組與隱式類型的數組

    這篇文章主要介紹了深入解析C#中的交錯數組與隱式類型的數組,隱式類型的數組通常與匿名類型以及對象初始值設定項和集合初始值設定項一起使用,需要的...

    C#教程網6172021-11-09
  • C#C#設計模式之Visitor訪問者模式解決長隆歡樂世界問題實例

    C#設計模式之Visitor訪問者模式解決長隆歡樂世界問題實例

    這篇文章主要介紹了C#設計模式之Visitor訪問者模式解決長隆歡樂世界問題,簡單描述了訪問者模式的定義并結合具體實例形式分析了C#使用訪問者模式解決長...

    GhostRider9502022-01-21
  • C#C#裁剪,縮放,清晰度,水印處理操作示例

    C#裁剪,縮放,清晰度,水印處理操作示例

    這篇文章主要為大家詳細介紹了C#裁剪,縮放,清晰度,水印處理操作示例,具有一定的參考價值,感興趣的小伙伴們可以參考一下...

    吳 劍8332021-12-08
  • C#Unity3D實現虛擬按鈕控制人物移動效果

    Unity3D實現虛擬按鈕控制人物移動效果

    這篇文章主要為大家詳細介紹了Unity3D實現虛擬按鈕控制人物移動效果,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一...

    shenqingyu060520232410972022-03-11
  • C#C#通過KD樹進行距離最近點的查找

    C#通過KD樹進行距離最近點的查找

    這篇文章主要為大家詳細介紹了C#通過KD樹進行距離最近點的查找,具有一定的參考價值,感興趣的小伙伴們可以參考一下...

    帆帆帆6112022-01-22
  • C#WPF 自定義雷達圖開發實例教程

    WPF 自定義雷達圖開發實例教程

    這篇文章主要介紹了WPF 自定義雷達圖開發實例教程,本文介紹的非常詳細,具有參考借鑒價值,需要的朋友可以參考下...

    WinterFish13112021-12-06
主站蜘蛛池模板: 久久久无码精品无码国产人妻丝瓜 | 久久精品国产免费播放 | 亚洲国产精品综合福利专区 | 毛片啪啪视频 | 国产在线观看人成激情视频 | 亚洲精品乱码久久久久久蜜桃 | 午夜免费体验30分 | piss美女厕所小便 | 护士被多人调教到失禁h | 亚洲AV永久无码精品澳门 | 欧美艳星kagneyiynn | 欧美亚洲国产另类 | 亚洲精品黄色 | 亚洲第一综合网站 | 九九热在线观看视频 | 日韩精品一区二区三区中文在线 | 草草视频免费观看 | 午夜爱情动作片P | 好男人资源免费播放 | juliaann大战黑人 | 美女被视频网站 | 胸奶好大好紧好湿好爽 | 金牛网155755水心论坛黄大父母 | 亚洲天堂中文 | 无码国产成人午夜在线观看不卡 | 亚洲天堂伦理 | 精品久久一 | 紧身牛仔裤美女被啪啪久久网 | 久久亚洲精品中文字幕60分钟 | 欧美视频在线一区二区三区 | а天堂中文最新版在线 | 成人国产网站v片免费观看 成人国产精品视频 | 欧美成人免费tv在线播放 | japanese日本护士| 亚洲欧美日韩国产精品影院 | 欧美日韩高清观看一区二区 | 蜜月aⅴ免费一区二区三区 蜜桃影像传媒推广 | 3d蒂法精品啪啪一区二区免费 | 青青青国产成人久久111网站 | 成年人在线视频观看 | 丝袜白浆 |