← 返回首页
设计模式基础教程(十二)
发表时间:2021-08-22 10:53:46
原型模式

1.原型模式

原型模式(Prototype Pattern):原型模式是一种对象创建型模式,用原型实例指定创建对象的种类,并且通过复制这些原型创建新的对象。原型模式允许一个对象再创建另外一个可定制的对象,无须知道任何创建的细节。 原型模式的基本工作原理是通过将一个原型对象传给那个要发动创建的对象,这个要发动创建的对象通过请求原型对象拷贝原型自己来实现创建过程。

通常情况下,一个类包含一些成员对象,在使用原型模式克隆对象时,根据其成员对象是否也克隆,原型模式可以分为两种形式:深克隆和浅克隆。在Java语言中,通过覆盖Object类的clone()方法可以实现浅克隆;如果需要实现深克隆,可以通过序列化(Serializable)等方式来实现。

2.实例

由于邮件对象包含的内容较多(如发送者、接收者、标题、内容、日期、附件等),某系统中现需要提供一个邮件复制功能,对于已经创建好的邮件对象,可以通过复制的方式创建一个新的邮件对象,如果需要改变某部分内容,无须修改原始的邮件对象,只需要修改复制后得到的邮件对象即可。使用原型模式设计该系统。在本实例中使用浅克隆实现邮件复制,即复制邮件(Email)的同时不复制附件(Attachment)。

这里我们以实现邮件的深克隆来举例讲解。

项目结构图如下:

定义附件类:

package com.simoniu.domain;
import java.io.Serializable;
public class Attachment implements Serializable {

    private String content;
    public Attachment(String content){
        this.content = content;
    }

    public void downLoad(){
        System.out.println("下载附件....");
        System.out.println("附件内容:"+this.content);
    }
}

定义邮件类

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.OptionalDataException;
import java.io.Serializable;

public class Email implements Serializable {
    private Attachment attachment;
    public Attachment getAttachment() {
        return attachment;
    }
    public Email(){
        this.attachment=new Attachment("New Title");
    }
    public Email(String title){
        this.attachment=new Attachment(title);
    }

    public Object deepClone() throws IOException, ClassNotFoundException, OptionalDataException{
        //将对象写入流
        ByteArrayOutputStream byteArrayOutputStream=new ByteArrayOutputStream();
        ObjectOutputStream objectOutputStream=new ObjectOutputStream(byteArrayOutputStream);
        objectOutputStream.writeObject(this);
        //将对象从流中取出
        ByteArrayInputStream byteArrayInputStream=new ByteArrayInputStream(byteArrayOutputStream.toByteArray());
        ObjectInputStream objectInputStream=new ObjectInputStream(byteArrayInputStream);
        return objectInputStream.readObject();
    }

    public void display(){
        System.out.println("查看邮件:"+this.attachment.toString());
    }
}

定义测试类

import com.simoniu.domain.Email;

public class TestDeepCloneableDemo01 {

    public static void main(String[] args) {
        Email email=new Email();
        try {
            Email copyEmail=(Email) email.deepClone();
            System.out.println("email==copyEmail?:"+(email==copyEmail));
            System.out.println("email.attachment==copyEmail.attachement?:"+(email.getAttachment()==copyEmail.getAttachment()));
            System.out.println("email.attachment hashCode:"+email.getAttachment().hashCode());
            System.out.println("copyEmail.attachment hashCode:"+copyEmail.getAttachment().hashCode());
            email.getAttachment().downLoad();;
            copyEmail.getAttachment().downLoad();
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}

运行结果:
email==copyEmail?:false
email.attachment==copyEmail.attachement?:false
email.attachment hashCode:356473385
copyEmail.attachment hashCode:1364614850
下载附件....
附件内容:New Title
下载附件....
附件内容:New Title