設計模式之原型模式

2021-08-06 06:58:06 字數 3868 閱讀 8878

定義:
根據現有的物件進行轉殖產生乙個新的物件。當直接進行物件建立效能消耗比較大的情形之下,即可用使用原型模式。 比如在建立一物件的時候,需要通過運算元據庫或者檔案才能被建立。這種情況之下我們就可以對已有的物件進行快取,然後在下次建立物件的時候返回,從而減少資料庫或者檔案的操作。

需要的角色:客戶端(client):具體呼叫者類。

抽象的原型類(prototype): 實現cloneable介面。 方便擴充套件。

具體的原型類(concreteprototype):客服端需要的物件, 重寫object的clone()方法,進行物件的轉殖。

使用場景:1、類初始化需要消耗很大的資源。

2、對效能和安全有較高的要求。

3、建立乙個物件需要大量的資料準備和訪問許可權。

4、物件可能被多個使用者修改。優點:1、對於需要產生大量物件的場景, 使用clone大大提高效能。

2、直接從記憶體中拷貝, 跳過了建構函式的約束。缺點:1、必須實現cloneable介面。

2、對於已經封裝好的類不容易實現。

3、逃避了建構函式的約束。使用示例:1、細胞**。

2、遊戲中大量相同物件(***遊戲中的子彈)。注意事項:1、原型模式是通過直接在記憶體中進行物件轉殖的,因此不會執行構造方法,而且訪問許可權也是無效的。原型模式和單例模式是衝突的。

2、clone()方法只會對基本資料型別(包括string)進行拷貝, 對於陣列、map、自定義物件等不會進行拷貝,如果需要,則需要進行深度拷貝(對這些資料另行進行拷貝)。

3、必須實現cloneable 介面,不然會丟擲clonenotsupportedexception異常。

4、clone()的訪問許可權為protected, 需要修改為public,不然在客戶端沒法呼叫。

示例**:

具體原型類(這只是簡單測試, 如果需要擴充套件,可以定義基類)

public class mobile implements cloneable 

public void setname(string name)

public void setbrand(string brand)

@override

public mobile clone() throws clonenotsupportedexception

@override

public string tostring()

}

客戶端測試**:

mobile mobile = new mobile();

mobile.setname("紅公尺note4");

mobile.setbrand("小公尺");

try catch (clonenotsupportedexception e)

測試結果: 從輸出的結果可以看出, 構造方法值被執行一次,說明後面兩個物件都是通過clone實現的,從而驗證了clone不呼叫構造方法的說法。

上面示例**中的物件的屬性採用的是string, 下面我們換成自定義物件試試:

自定義屬性類:

public class brand  

public void setname(string name)

public string getsysversion()

public void setsysversion(string sysversion)

@override

public string tostring()

}

具體原型類中**修改:

public class mobile implements cloneable 

public void setname(string name)public void setbrand(string name, string sysversion)@override

public mobile clone() throws clonenotsupportedexception

@override

public string tostring()

}

客戶端測試**:
mobile mobile = new mobile();

mobile.setname("紅公尺note4");

mobile.setbrand("小公尺", "6.0");

try catch (clonenotsupportedexception e)

測試結果:通過測試結果可以看出, 自定義屬性並沒有被clone,只是後面的賦值替換前面的賦值,從而以驗證了clone()方法只能對基本資料型別以及string型別進行clone,而不能對陣列、map、自定義資料型別進行clone(這就是常說的淺轉殖)。

那怎樣能實現對自定義資料型別進行拷貝呢? 實現很簡單,進行深度轉殖即可,即對自定義資料型別進行單獨轉殖,示例**如下:

自定義資料類: 需要實現cloneable介面, 重寫clone()方法。

public class brandimplements cloneablepublic void setname(string name) 

public string getsysversion()

public void setsysversion(string sysversion)@override

public brand clone() throws clonenotsupportedexception @override

public string tostring()

}

具體原型類中**

public class mobile implements cloneable 

public void setname(string name)

public void setbrand(string name, string sysversion)

@override

public mobile clone() throws clonenotsupportedexception

@override

public string tostring()

}

客戶端測試**:

mobile mobile = new mobile();

mobile.setname("紅公尺note4");

mobile.setbrand("小公尺", "6.0");

try catch (clonenotsupportedexception e)

測試結果:從測試結果看出,我們實現了深度轉殖。

設計模式之原型模式

原型模式其實就是從乙個物件再建立乙個可定製的物件,而且不需要知道建立的細節。具體就是說通過複製或者轉殖乙個原型物件產生新的物件 轉殖物件 分為兩種 深複製或者淺複製,這兩種的主要區別是 在原型中如果有物件的引用,淺複製是將引用複製過來了,也就是淺複製和原型中的物件的引用相同,而深複製是將轉殖物件中引...

設計模式之原型模式

include include 此練習為原型模式方法的練習 原型模式揭示了在同一原型上可以通過複製使得 只需要例項化一次,再通過相應的類函式操作可以得到 同一原型下的不同的版本物件 此練習將考慮在實際開發中 比如 工作經歷也是作為乙個類被含在簡歷類中的情況 這情況將涉及到類的引用和深 淺複製 原型基...

設計模式之原型模式

原型模式的思想就是將乙個物件作為原型,對其進行複製 轉殖,產生乙個和原物件類似的新物件 複製過程可分為淺複製和深複製。淺複製是指直接呼叫父類 即object類 的clone方法 super.clone 該方法是本地 native 方法,呼叫該方法clone出來的新物件,基本資料型別的屬性變數是新建立...