原型模式 可以理解为深复制对象,之前开发的时候自己经常用,但是不知道它还有这个名字。
类图如下(可以不看):
普通复制方法:
类中有一个 复制对象的方法。
/**
* 订单对象
*/
public class OrderObject {
private String id;//订单id
private String name;//订单名
private double price;//价格
/**
* 复制订单 原型模式
*/
public OrderObject cloneOrder(){
OrderObject orderObject = new OrderObject();
orderObject.setId(this.getId());
orderObject.setName(this.getName());
orderObject.setPrice(this.getPrice());
return orderObject;
}
//getter and setter
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
}
测试方法:
public static void main(String[] args) {
OrderObject object1 = new OrderObject();
object1.setId("123");
object1.setPrice(12.12);
object1.setName("订单名");
OrderObject object2 = object1.cloneOrder();
object2.setPrice(object1.getPrice() + 10);
System.out.println("object1:"+object1 +" 价格:"+object1.getPrice());
System.out.println("object2:"+object2 +" 价格:"+object2.getPrice());
}
运行结果:
object1:com.teligen.dazt.learn.design.prototype.OrderObject@52cc8049 价格:12.12
object2:com.teligen.dazt.learn.design.prototype.OrderObject@5b6f7412 价格:22.119999999999997
上述的复制逻辑有点复杂,我们可以写一个万能的复制方法(基于流复制),但是类需要可序列化。
复制方法如下:
ReflexUtil.java 下的方法
/**
* 基于流的深复制
* @param t 要复制的对象
* @param <T> 类型
*/
public static <T> T cloneObject(T t){
ByteArrayOutputStream bos = null;
ObjectOutputStream oos = null;
try {
bos = new ByteArrayOutputStream();
oos = new ObjectOutputStream(bos);
oos.writeObject(t);
oos.flush();
ObjectInputStream ois = new ObjectInputStream(new ByteArrayInputStream(bos.toByteArray()));
T cloneT = (T) ois.readObject();
return cloneT;
}catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if(bos != null){
bos.close();
}
} catch (IOException e) {
e.printStackTrace();
}
try {
if(oos != null){
oos.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
return null;
}
使用方法:
1:对象需要可序列化
public class OrderObject implements Serializable {...}
2:测试
OrderObject orderObject = new OrderObject();
orderObject.setId("123");
orderObject.setName("订单123");
orderObject.setPrice(10.1);
OrderObject orderObject2 = ReflexUtil.cloneObject(orderObject);
System.out.println(orderObject +" name:"+orderObject.getName());
System.out.println(orderObject2+" name:"+orderObject2.getName());
测试结果:
com.teligen.dazt.learn.design.prototype.OrderObject@3941a79c name:订单123
com.teligen.dazt.learn.design.prototype.OrderObject@133314b name:订单123