原型模式:有一个对象A,在不使用创建的情况下,得到一个与A一样的对象AC。AC即被称为原型。
实现这个模式,一般使用克隆的方式,需要实现Cloneable接口。
也就是使用JAVA的克隆技术。
克隆分为“深克隆”、“浅克隆”。
深克隆需要实现Serializable接口,使用 流 技术。
浅克隆只需要实现Cloneable接口,重写clone方法。
代码如下:请注意观察结果内,数据的不同,对象地址的不同。
浅克隆
package com.mkf.pattern; import java.io.Serializable; public class ClassOne implements Serializable { private static final long serialVersionUID = -1393695894851384014L; private String str; public String getStr() { return str; } public void setStr(String str) { this.str = str; } } package com.mkf.pattern; public class PrototypePattern implements Cloneable { private String str; private Integer ieg; private ClassOne co; @Override public PrototypePattern clone() throws CloneNotSupportedException { return (PrototypePattern) super.clone(); } public String getStr() { return str; } public void setStr(String str) { this.str = str; } public Integer getIeg() { return ieg; } public void setIeg(Integer ieg) { this.ieg = ieg; } public ClassOne getCo() { return co; } public void setCo(ClassOne co) { this.co = co; } /** * 浅克隆 */ public static void test1() throws CloneNotSupportedException { ClassOne co = new ClassOne(); co.setStr("iop"); PrototypePattern pp = new PrototypePattern(); pp.setStr("abc"); pp.setIeg(123); pp.setCo(co); PrototypePattern pp1 = pp.clone(); System.out.println(pp1.getStr() + "\t" + pp1.getIeg() + "\t" + pp1.getCo().getStr() + "\t" + pp1.getCo() + "\t" + pp1); pp1.setStr("xyz"); pp1.setIeg(456); pp1.getCo().setStr("qwe"); System.out.println(pp.getStr() + "\t" + pp.getIeg() + "\t" + pp.getCo().getStr() + "\t" + pp.getCo() + "\t" + pp); pp.setStr("hij"); pp.setIeg(789); pp.getCo().setStr("fgh"); System.out.println(pp1.getStr() + "\t" + pp1.getIeg() + "\t" + pp1.getCo().getStr() + "\t" + pp1.getCo() + "\t" + pp1); System.out.println(pp.getStr() + "\t" + pp.getIeg() + "\t" + pp.getCo().getStr() + "\t" + pp.getCo() + "\t" + pp); } public static void main(String[] args) throws CloneNotSupportedException { test1(); } }
浅克隆结果:
abc 123 iop com.mkf.pattern.ClassOne@61de33 com.mkf.pattern.PrototypePattern@14318bb
abc 123 qwe com.mkf.pattern.ClassOne@61de33 com.mkf.pattern.PrototypePattern@ca0b6
xyz 456 fgh com.mkf.pattern.ClassOne@61de33 com.mkf.pattern.PrototypePattern@14318bb
hij 789 fgh com.mkf.pattern.ClassOne@61de33 com.mkf.pattern.PrototypePattern@ca0b6
深克隆:
package com.mkf.pattern; import java.io.Serializable; public class ClassOne implements Serializable { private static final long serialVersionUID = -1393695894851384014L; private String str; public String getStr() { return str; } public void setStr(String str) { this.str = str; } } package com.mkf.pattern; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; import java.io.Serializable; public class PrototypePatternTwo implements Cloneable, Serializable { private static final long serialVersionUID = -2021064356103593636L; private String str; private Integer ieg; private ClassOne co; public Object deepClone() throws Exception { ByteArrayOutputStream bos = new ByteArrayOutputStream(); ObjectOutputStream oos = new ObjectOutputStream(bos); oos.writeObject(this); ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray()); ObjectInputStream ois = new ObjectInputStream(bis); return ois.readObject(); } public String getStr() { return str; } public void setStr(String str) { this.str = str; } public Integer getIeg() { return ieg; } public void setIeg(Integer ieg) { this.ieg = ieg; } public ClassOne getCo() { return co; } public void setCo(ClassOne co) { this.co = co; } /** * 深克隆 */ public static void test1() throws Exception { ClassOne co = new ClassOne(); co.setStr("iop"); PrototypePatternTwo pp = new PrototypePatternTwo(); pp.setStr("abc"); pp.setIeg(123); pp.setCo(co); PrototypePatternTwo pp1 = (PrototypePatternTwo) pp.deepClone(); System.out.println(pp1.getStr() + "\t" + pp1.getIeg() + "\t" + pp1.getCo().getStr() + "\t" + pp1.getCo() + "\t" + pp1); pp1.setStr("xyz"); pp1.setIeg(456); pp1.getCo().setStr("qwe"); System.out.println(pp.getStr() + "\t" + pp.getIeg() + "\t" + pp.getCo().getStr() + "\t" + pp.getCo() + "\t" + pp); pp.setStr("hij"); pp.setIeg(789); pp.getCo().setStr("fgh"); System.out.println(pp1.getStr() + "\t" + pp1.getIeg() + "\t" + pp1.getCo().getStr() + "\t" + pp1.getCo() + "\t" + pp1); System.out.println(pp.getStr() + "\t" + pp.getIeg() + "\t" + pp.getCo().getStr() + "\t" + pp.getCo() + "\t" + pp); } public static void main(String[] args) throws Exception { test1(); } }
深克隆结果:
abc 123 iop com.mkf.pattern.ClassOne@c20e24 com.mkf.pattern.PrototypePatternTwo@2e7263
abc 123 iop com.mkf.pattern.ClassOne@a62fc3 com.mkf.pattern.PrototypePatternTwo@530daa
xyz 456 qwe com.mkf.pattern.ClassOne@c20e24 com.mkf.pattern.PrototypePatternTwo@2e7263
hij 789 fgh com.mkf.pattern.ClassOne@a62fc3 com.mkf.pattern.PrototypePatternTwo@530daa