1.模式描述
用原型实例指定创建对象的种类,并且通过拷贝来创建新的对象。
2.模式作用
可以一定程度上解耦,消费者和对象的构造过程隔离开,对象如何构造与消费者完全无关。
可以一定程度提升效率,复杂对象的构造往往需要较长的时间(中间可能会进行复杂运算或者数据库交互),clone消耗的资源一般情况下会少很多。
可以一定程度增加代码的封装性,避免复杂的构造过程。
等等。//TODO
3.适用场景
需要创建一个复杂的、构造耗时很多的对象,且已有一个同类对象的时候。
消费者不关心对象构造过程的时候。
等等。//TODO
例如:工作流实例的重建、复杂数据实体的复制
4.模式要素
该类要支持克隆。该类要实现Cloneable接口。
已有该类的一个实例。该实例作为原型进行clone。
该类的克隆方法应为深克隆。该类中除了8中基本类型(以及他们的封装类)、String(其实是浅clone,但是了解一下String就会发现其实结果和深clone一致,这里我们认为就是深clone)之外的属性均需要进行深clone;或者采用流化clone方式进行深clone。
5.类图
6.模式实例代码
原型:
[java] view plain copy
- package com.demoFound.prototype;
- import java.io.ByteArrayInputStream;
- import java.io.ByteArrayOutputStream;
- import java.io.IOException;
- import java.io.ObjectInputStream;
- import java.io.ObjectOutputStream;
- import java.io.Serializable;
- import java.util.List;
- /**
- * 原型模式_原型类
- *
- * @author popkidorc
- *
- */
- public class MyPrototypeProcessInstance implements Serializable, Cloneable {
- // 只有实现了Clonealbe接口,虚拟机才会认为clone是可用的,不然会抛出CloneNotSupportedException
- // 实现Serializable是为了可以进行流化clone,该clone为深clone
- private static final long serialVersionUID = 1L;
- private String processInstanceId;
- private String processTitle;
- private String processDefinitionId;
- private String processStatus;
- private List<MyPrototypeTaskInstance> taskInstances;
- public String getProcessInstanceId() {
- return processInstanceId;
- }
- public void setProcessInstanceId(String processInstanceId) {
- this.processInstanceId = processInstanceId;
- }
- public String getProcessTitle() {
- return processTitle;
- }
- public void setProcessTitle(String processTitle) {
- this.processTitle = processTitle;
- }
- public String getProcessDefinitionId() {
- return processDefinitionId;
- }
- public void setProcessDefinitionId(String processDefinitionId) {
- this.processDefinitionId = processDefinitionId;
- }
- public String getProcessStatus() {
- return processStatus;
- }
- public void setProcessStatus(String processStatus) {
- this.processStatus = processStatus;
- }
- public List<MyPrototypeTaskInstance> getTaskInstances() {
- return taskInstances;
- }
- public void setTaskInstances(List<MyPrototypeTaskInstance> taskInstances) {
- this.taskInstances = taskInstances;
- }
- @Override
- public MyPrototypeProcessInstance clone() throws CloneNotSupportedException {
- // 浅clone,对taskInstances来说仍然是引用,2个对象使用一个taskInstances
- // return (MyPrototypeProcessInstance) super.clone();
- // 深clone,传统方式
- // MyPrototypeProcessInstance myPrototypeProcessInstanceClone =
- // (MyPrototypeProcessInstance) super
- // .clone();
- // // 非8基本类型或者String,需要通过new,然后为其copy值的方式来clone
- // List<MyPrototypeTaskInstance> myPrototypeTaskInstancesClone = new
- // ArrayList<MyPrototypeTaskInstance>();
- // for (MyPrototypeTaskInstance myPrototypeTaskInstance : this
- // .getTaskInstances()) {
- // myPrototypeTaskInstancesClone.add(myPrototypeTaskInstance.clone());
- // }
- // myPrototypeProcessInstanceClone
- // .setTaskInstances(myPrototypeTaskInstancesClone);
- // return myPrototypeProcessInstanceClone;
- // 深clone,流化方式,需要实现Serializable
- ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
- ObjectOutputStream objectOutputStream;
- try {
- objectOutputStream = new ObjectOutputStream(byteArrayOutputStream);
- // 写入流
- objectOutputStream.writeObject(this);
- ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(
- byteArrayOutputStream.toByteArray());
- ObjectInputStream objectInputStream = new ObjectInputStream(
- byteArrayInputStream);
- // 读出流
- return (MyPrototypeProcessInstance) objectInputStream.readObject();
- } catch (IOException e) {
- System.out.println("==IOException==");
- } catch (ClassNotFoundException e) {
- System.out.println("==ClassNotFoundException==");
- }
- return null;
- }
- }
[java] view plain copy
- package com.demoFound.prototype;
- import java.io.Serializable;
- /**
- * 原型模式_原型类的子类
- *
- * @author popkidorc
- *
- */
- public class MyPrototypeTaskInstance implements Serializable, Cloneable {
- private static final long serialVersionUID = 1L;
- private String taskInstanceId;
- private String taskInstanceUser;
- public String getTaskInstanceId() {
- return taskInstanceId;
- }
- public void setTaskInstanceId(String taskInstanceId) {
- this.taskInstanceId = taskInstanceId;
- }
- public String getTaskInstanceUser() {
- return taskInstanceUser;
- }
- public void setTaskInstanceUser(String taskInstanceUser) {
- this.taskInstanceUser = taskInstanceUser;
- }
- @Override
- public MyPrototypeTaskInstance clone() throws CloneNotSupportedException {
- return (MyPrototypeTaskInstance) super.clone();
- }
- }
消费者:
[java] view plain copy
- package com.demoFound.prototype;
- import java.util.ArrayList;
- /**
- * 原型模式_消费者类
- *
- * @author popkidorc
- *
- */
- public class MyPrototypeMain {
- private static MyPrototypeProcessInstance myPrototypeProcessInstance;
- private static void initMyPrototypeProcessInstance() {
- // 构造一个MyPrototypeProcessInstance,并为其赋值
- myPrototypeProcessInstance = new MyPrototypeProcessInstance();
- myPrototypeProcessInstance.setProcessDefinitionId("PROC001");
- myPrototypeProcessInstance.setProcessInstanceId("PROCINST00001");
- myPrototypeProcessInstance.setProcessStatus("S0102");
- myPrototypeProcessInstance.setProcessTitle("流程实例测试");
- ArrayList<MyPrototypeTaskInstance> taskInstances = new ArrayList<MyPrototypeTaskInstance>();
- MyPrototypeTaskInstance myPrototypeTaskInstance1 = new MyPrototypeTaskInstance();
- myPrototypeTaskInstance1.setTaskInstanceId("TASK00001");
- myPrototypeTaskInstance1.setTaskInstanceUser("testUser001");
- taskInstances.add(myPrototypeTaskInstance1);
- // 这里就不用clone了,直接new
- MyPrototypeTaskInstance myPrototypeTaskInstance2 = new MyPrototypeTaskInstance();
- myPrototypeTaskInstance2.setTaskInstanceId("TASK00002");
- myPrototypeTaskInstance2.setTaskInstanceUser("testUser002");
- taskInstances.add(myPrototypeTaskInstance2);
- myPrototypeProcessInstance.setTaskInstances(taskInstances);
- }
- public static void main(String[] args) {
- initMyPrototypeProcessInstance();
- // 开始clone
- MyPrototypeProcessInstance myPrototypeProcessInstanceClone = null;
- try {
- myPrototypeProcessInstanceClone = myPrototypeProcessInstance
- .clone();
- // 只有实例id、状态和task的user变化
- myPrototypeProcessInstanceClone
- .setProcessInstanceId("PROCINST00002");
- myPrototypeProcessInstanceClone.setProcessStatus("S0101");
- myPrototypeProcessInstanceClone.getTaskInstances().get(0)
- .setTaskInstanceUser("testUser003");
- myPrototypeProcessInstanceClone.getTaskInstances().get(1)
- .setTaskInstanceUser("testUser004");
- } catch (CloneNotSupportedException e) {
- System.out.println("CloneNotSupportedException");
- }
- // 比对结果
- System.out.println("==myPrototypeProcessInstance=="
- + myPrototypeProcessInstance.getProcessInstanceId());
- for (MyPrototypeTaskInstance myPrototypeTaskInstance : myPrototypeProcessInstance
- .getTaskInstances()) {
- System.out.println("==myPrototypeProcessInstance=="
- + myPrototypeTaskInstance.getTaskInstanceUser());
- }
- System.out.println("==myPrototypeProcessInstanceClone=="
- + myPrototypeProcessInstanceClone.getProcessInstanceId());
- // 若是浅clone可以看到taskInstances为一个内存,只是2个对象均引用了taskInstances;若是深clone,则会为2个对象的taskInstances分别分配内存
- for (MyPrototypeTaskInstance myPrototypeTaskInstance : myPrototypeProcessInstanceClone
- .getTaskInstances()) {
- System.out.println("==myPrototypeProcessInstanceClone=="
- + myPrototypeTaskInstance.getTaskInstanceUser());
- }
- }
- }
原文地址:http://blog.csdn.net/ooppookid/article/details/42914173