-
Notifications
You must be signed in to change notification settings - Fork 0
原型模式
ZHI-XINHUA edited this page Jan 11, 2019
·
1 revision
在JAVA语言中使用原型模式是非常简单的,这是因为Object类当中提供了一个本地方法clone,而JAVA中的任何类只要实现了Cloneable标识接口,就可以使用clone方法来进行对象的拷贝。
复制时构造方法是不被执行
被复制对象所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用都仍然指向 原来的对象。
直接使用object 的clone方法复制:
public Apple clone() {
Apple apple = null;
try {
apple = (Apple)super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return apple;
}
被复制对象的所有变量都包含与原来的对象相同的值,除去那些应用其他对象的变量。引用其他变量的对象将指向被复制过的新对象,而不再是原来的那些被引用的对象。换言之,深度复制就是复制的对象所引用的对象都复制咯一遍,而这种对被引用到的对象的复制叫做间接复制。
引用的对象也要自己实现复制
public Apple depthClone(){
Apple apple = null;
try {
apple = (Apple)super.clone();
apple.producingPlace = producingPlace.clone();//复制引用对象
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return apple;
}
完整栗子:
package com.prototype;
public class Apple implements Cloneable {
private String varieties;
private float weight;
private String color;
private ProducingPlace producingPlace;
public Apple(String varieties,float weight,String color,ProducingPlace producingPlace){
this.varieties = varieties;
this.weight =weight;
this.color = color;
this.producingPlace = producingPlace;
System.out.println("Apple constructor");
}
/**
* 浅度复制:被复制对象所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用都仍然指向
* 原来的对象。
* @return
*/
public Apple clone() {
Apple apple = null;
try {
apple = (Apple)super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return apple;
}
/**
* 深度复制:被复制对象的所有变量都包含与原来的对象相同的值,除去那些应用其他对象的变量。
* 引用其他变量的对象将指向被复制过的新对象,而不再是原来的那些被引用的对象。
* 换言之,深度复制就是复制的对象所引用的对象都复制咯一遍,而这种对被引用到的对象的复制叫做间接复制
* @return
*/
public Apple depthClone(){
Apple apple = null;
try {
apple = (Apple)super.clone();
apple.producingPlace = producingPlace.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return apple;
}
@Override
public String toString() {
return "varieties:"+this.varieties+" weight:"+this.weight+" color:"+this.color+" producingPlace:"+producingPlace;
}
public float getWeight() {
return weight;
}
public void setWeight(float weight) {
this.weight = weight;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
public String getVarieties() {
return varieties;
}
public void setVarieties(String varieties) {
this.varieties = varieties;
}
public ProducingPlace getProducingPlace() {
return producingPlace;
}
public void setProducingPlace(ProducingPlace producingPlace) {
this.producingPlace = producingPlace;
}
}
package com.prototype;
public class ProducingPlace implements Cloneable{
private String province;
private String city;
public ProducingPlace(String province,String city){
this.province = province;
this.city =city;
System.out.println("ProducingPlace constructor");
}
public ProducingPlace clone(){
ProducingPlace p = null;
try {
p = (ProducingPlace)super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return p;
}
@Override
public String toString() {
return "ProducingPlace:"+super.toString();
}
public String getProvince() {
return province;
}
public void setProvince(String province) {
this.province = province;
}
public String getCity() {
return city;
}
public void setCity(String city) {
this.city = city;
}
}
测试:
package com.prototype;
public class PrototypeMain {
public static void main(String[] args) {
ProducingPlace p = new ProducingPlace("guangdong","guangzhou");
Apple apple = new Apple("gz",2,"red",p);
System.out.println("===clone====");
System.out.println("original=="+apple.toString());
Apple cloneApple = apple.clone();
System.out.println("clone=="+cloneApple.toString());
System.out.println("========depthClone========");
System.out.println("original==" +apple.toString());
Apple depthCloneApple = apple.depthClone();
System.out.println("depthClone=="+depthCloneApple.toString());
}
}
//使用序列化和反序列化实现深复制
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(bos);
oos.writeObject(s1);
byte[] bytes = bos.toByteArray();
ByteArrayInputStream bis = new ByteArrayInputStream(bytes);
ObjectInputStream ois = new ObjectInputStream(bis);
Sheep s2 = (Sheep) ois.readObject(); //克隆好的对象!
结果:
ProducingPlace constructor
Apple constructor
===clone====
original==varieties:gz weight:2.0 color:red producingPlace:ProducingPlace:com.prototype.ProducingPlace@3796751b
clone==varieties:gz weight:2.0 color:red producingPlace:ProducingPlace:com.prototype.ProducingPlace@3796751b
========depthClone========
original==varieties:gz weight:2.0 color:red producingPlace:ProducingPlace:com.prototype.ProducingPlace@3796751b
depthClone==varieties:gz weight:2.0 color:red producingPlace:ProducingPlace:com.prototype.ProducingPlace@3796751b
原型模式很少单独出现,一般是和工厂方法模式一起出现,通过clone的方法创建一个对象,然后由工厂方法提供给调用者。
- spring中bean的创建实际就是两种:单例模式和原型模式。(当然,原型模式需要和工厂模式搭配起来)
设计模式