原型模式prototype
1. 通过new产生一个对象需要非常繁琐的数据准备或访问权限,则可以使用原型模式。
2. 就是java中的克隆技术,以某个对象为原型,复制出新的对象,显然,新的对象具备原型对象的接入点。
3. 优势:效率高(直接克隆,避免了重新执行构造过程步骤)
4. 克隆类似于new,但是不同于new,new创建新的对象属性采用的是默认值,克隆出的对象的属性值完全和原型对象相同,并且克隆出的新对象改变不会影响原型对象,然后再修改克隆对象的值.
原型模式实现:
实现Cloneable接口和重写Object的clone方法
浅克隆存在的问题
被复制的对象的所有变量都从含有与原来的对象相同的值,而所有的对其他对象的引用都仍然指向原来的对象
深克隆如何实现
1. 深克隆把引用的变量指向复制过的新的对象,而不是原有的被引用的对象。
2. 让已实现Cloneable接口类中的属性也实现Cloneable接口
3. 基本数据类型和String能够自动实现深度克隆(值的复制)
应用场景
原型模式很少单独出现,一般是和工厂方法模式一起出现,通过clone的方法创建一个对象,然后由工厂方法提供给调用者
浅克隆
package designmode.prototype;
import java.util.Date;
public class Sheep implements Cloneable {
private String name;
private Date birthday;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
protected Object clone() throws CloneNotSupportedException{
Object obj = super.clone();
return obj;
}
public Sheep() {
}
public Sheep(String name, Date birthday) {
this.name = name;
this.birthday = birthday;
}
}
深克隆
package designmode.prototype;
import java.util.Date;
public class Ovine implements Cloneable{
private String name;
private Date birthday;
public Ovine() {
}
public Ovine(String name, Date bithday) {
super();
this.name = name;
this.birthday = bithday;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date bithday) {
this.birthday = bithday;
}
protected Object clone() throws CloneNotSupportedException{
Object obj = super.clone();
Ovine o = (Ovine) obj;
o.birthday = (Date) this.birthday.clone();
return obj;
}
}
测试
package designmode.prototype;
import java.util.Date;
/**
* 原型模式(浅克隆)
* @author baiyi
*
*/
public class PrototypeTest {
public static void main(String[] args) throws CloneNotSupportedException {
Sheep s1 = new Sheep("多莉",new Date(12345988799L));
System.out.println(s1);
System.out.println(s1.getName());
System.out.println(s1.getBirthday());
Sheep s2 = (Sheep) s1.clone();
System.out.println(s2);
System.out.println(s2.getName()+ s2.getBirthday());
s2.setName("多莉莉");
s2.setBirthday(new Date(18773445555555L));
System.out.println("修改后:"+ s2.getName() + "出生于:" + s2.getBirthday());
}
}