1、什么是原型模式?
通过复制生成实例,包括深拷贝和浅拷贝。
2、类图
摘录:《图解设计模式》书籍
在 Prototype模式中有以下登场角色。
Prototype(原型)
Product角色负责定义用于复制现有实例来生成新实例的方法。在示例程序中,由Product接口扮演此角色。
ConcretePrototype(具体的原型)
ConcretePrototype角色负责实现复制现有实例并生成新实例的方法。在示例程序中,由MessageBox类和 UnderlinePen类扮演此角色。
Client(使用者)
Client角色负责使用复制实例的方法生成新的实例。在示例程序中,由Manager类扮演此角色。
3、案例
参考案例:https://www.jianshu.com/p/1939fbe5dfdb
我们先定义一个接口,Product接口,这个接口是复制功能的接口,继承了cloneable接口
public interface Product extends Cloneable {
public abstract void use(String s);
public abstract Product createClone();
}
createClone是用来复制实例的方法,use方法是用来使用实例方法的。这些方法具体都交给子类去实现。
我们实现一个具体的子类,MessageBox,它的作用是可以给字符创添加类似方框的边界的图案。
这个类实现了product接口,createClone是用于复制自己,生成一个新的一模一样的实例,也就是原型模式的思想。use方法将结果显示出来。
public class MessageBox implements Product {
private char decochar;
public MessageBox(char decochar) {
this.decochar = decochar;
}
public void use(String s) {
int length = s.getBytes().length;
for (int i = 0; i < length + 4; i++) {
System.out.print(decochar);
}
System.out.println("");
System.out.println(decochar + " " + s + " " + decochar);
for (int i = 0; i < length + 4; i++) {
System.out.print(decochar);
}
System.out.println("");
}
public Product createClone() {
Product p = null;
try {
p = (Product)clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return p;
}
}
同样的我们实现可以给字符串添加下划线的类UnderlinePen
这个类同样实现了product接口,并且可以复制自己生成一个新的实例。
public class UnderlinePen implements Product {
private char ulchar;
public UnderlinePen(char ulchar) {
this.ulchar = ulchar;
}
public void use(String s) {
int length = s.getBytes().length;
System.out.println("\"" + s + "\"");
System.out.print(" ");
for (int i = 0; i < length; i++) {
System.out.print(ulchar);
}
System.out.println("");
}
public Product createClone() {
Product p = null;
try {
p = (Product)clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return p;
}
}
最后我们新建一个管理类Manager来管理这些对象的创建,复制和使用。
Manager类中有一个map字段,用来存储product对象。create方法根据对象的名字在map找到对象的实例,然后调用实例的createClone方法,从而复制出一个实例。
public class Manager {
private HashMap showcase = new HashMap();
public void register(String name, Product proto) {
showcase.put(name, proto);
}
public Product create(String protoname) {
Product p = (Product)showcase.get(protoname);
return p.createClone();
}
}
我们来测试一下:
public class Main {
public static void main(String[] args) {
Manager manager = new Manager();
UnderlinePen upen = new UnderlinePen('~');
MessageBox mbox = new MessageBox('*');
MessageBox sbox = new MessageBox('/');
manager.register("strong message", upen);
manager.register("warning box", mbox);
manager.register("slash box", sbox);
Product p1 = manager.create("strong message");
p1.use("Hello, world.");
Product p2 = manager.create("warning box");
p2.use("Hello, world.");
Product p3 = manager.create("slash box");
p3.use("Hello, world.");
}
}
运行结果:
4、spring中 单例模式和原型模式的区别?
单例模式多次调用hashcode是相同的。
原型模式多次调用hashcode是不同的。