[漁夫也能懂設計模式] 原型模式(Prototype pattern)

原型模式是創建型模式的一種,其特點在於通過「複製」一個已經存在的實例來返回新的實例,而不是新建實例。被複制的實例就是我們所稱的「原型」,這個原型是可定製的。

在這裏插入圖片描述   Prototype原型模式是一種創建型設計模式,它主要面對的問題是:“某些結構複雜的對象”的創建工作;由於需求的變化,這些對象經常面臨着劇烈的變化,但是他們卻擁有比較穩定一致的接口。

    例子:

public class WeeklyLog implements Cloneable
{
    private String name;
    private String date;
    private String content;
    public void setName(String name){
        this.name = name;
    }
    public void setDate(String date){
        this.date = date;
    }
    public void setContent(String content){
        this.content = content;
    }
    public String getName(){
        return (this.name);
    }
    public String getDate(){
        return (this.date);
    }
    public String getContent(){
        return (this.content);
    }

    public Object clone()
    {
        Object obj = null;
        try
        {
            obj = super.clone();
            return obj;
        }
        catch (CloneNotSupportedException e)
        {
            System.out.println("不能複製!");
            return null;
        }
    }

}

public class Client
{
    public static void main(String[] args) {
        WeeklyLog log_previous = new WeeklyLog();
        log_previous.setName("張三");
        log_previous.setDate("2018年 第 12 周");
        log_previous.setContent("這周工作很忙,每天加班!");

        System.out.println("*** 週報 ***");
        System.out.println(log_previous.getDate());
        System.out.println(log_previous.getName());
        System.out.println(log_previous.getContent());
        System.out.println("-----------------------------------------");

        WeeklyLog log_now;
        log_now = (WeeklyLog)log_previous.clone();
        log_now.setDate("2018年 第 13 周");
        System.out.println("*** 週報 ***");
        System.out.println(log_now.getDate());
        System.out.println(log_now.getName());
        System.out.println(log_now.getContent());
    }
}

   在本實例中使用了Java語言內置的潛克隆機制,通過繼承Object類的clone()方法實現對象的複製,原始對象和克隆得到的對象在內存中是兩個完全不同的對象,通過已創建的工作週報可以快速創建新的週報,然後再根據需要修改週報,無須再從頭開始創建。原型模式爲工作流系統中任務單的快速生成提供了一種解決方案。

淺克隆和深克隆

   無論你是自己實現克隆方法,還是採用Java提供的克隆方法,都存在一個淺度克隆和深度克隆的問題。

  • 淺度克隆

   只負責克隆按值傳遞的數據(比如基本數據類型、String類型),而不復制它所引用的對象,換言之,所有的對其他對象的引用都仍然指向原來的對象。

  • 深度克隆

    除了淺度克隆要克隆的值外,還負責克隆引用類型的數據。那些引用其他對象的變量將指向被複制過的新對象,而不再是原有的那些被引用的對象。換言之,深度克隆把要複製的對象所引用的對象都複製了一遍,而這種對被引用到的對象的複製叫做間接複製。

    深度克隆要深入到多少層,是一個不易確定的問題。在決定以深度克隆的方式複製一個對象的時候,必須決定對間接複製的對象時採取淺度克隆還是繼續採用深度克隆。因此,在採取深度克隆時,需要決定多深纔算深。此外,在深度克隆的過程中,很可能會出現循環引用的問題,必須小心處理。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章