原型模式——clone

设计模式之禅学习——原型模式

1、原型模式非常简单,要使用原型模式时只要将被clone的类继承Cloneable接口,并重写clone()方法就可以。

2、原型模式的原理是内存二进制流的拷贝,要比直接New出一个对象快得多,性能能够得到很大提升。当我们       要产生大量一个类的对象时,这些对象只是细节上不同,这时就可以通过原型模式提高代码的效率。原型模       式一般不会单独使用,一般和工厂模式在一起,同clone的方法创建一个对象,然后由工厂方法。,提供给         调用者。

3、一个原型模式的例子:

package com.wang.prototypePattern;

/**
 * 原型模式
 * @author HeJW
 *
 */
public class PrototypeClass implements Cloneable {

	public PrototypeClass(){
		System.out.println("创建");
	}
	
	@Override
	protected PrototypeClass clone() {
		
		PrototypeClass prototypeClass = null;
	
		try {
			prototypeClass = (PrototypeClass)super.clone();
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		
		return prototypeClass;	
	}
}

在使用时:

package com.wang.prototypePattern;

public class App {
	
	public static void main(String[] args) {
		
		PrototypeClass prototypeClass1 = new PrototypeClass();
		PrototypeClass prototypeClass2 = prototypeClass1.clone();
		
	}
}

4、在拷贝对象时,会有深拷贝和浅拷贝的区别,首先看浅拷贝的代码:

package com.wang.prototypePattern.develop;

import java.util.ArrayList;

/**
 * 浅拷贝
 * 
 * @author HeJW
 * 
 */
public class QianClone implements Cloneable {

	private ArrayList<String> arrayList = new ArrayList<String>();

	@Override
	protected QianClone clone() {

		QianClone qian = null;
		try {
			qian = (QianClone) super.clone();
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		return qian;
	}
	
	public void setValue( String value ){
		this.arrayList.add(value);
	}
	
	public ArrayList<String> getValue(){
		return this.arrayList;
	}
	
	public static void main(String[] args) {
		
		QianClone qian = new QianClone();
		qian.setValue("张三");
		
		QianClone qianClone = qian.clone();
		qianClone.setValue("李四");
		
		System.out.println(qian.getValue());
	}

}

    执行后的结果是:

[张三, 李四]

     为什么会有李四呢,没有对arrayList进行clone啊。是因为java在clone时,只是clone本对象,其对象内部数组、引用对象都不clone,还是指向原生对象,这就是浅拷贝,多个对象共享一个私有变量,不安全。

     再来看深拷贝,只是比浅拷贝多一句代码,让不同的对象使用其自己clone的私有变量,不共同使用一个:

package com.wang.prototypePattern.develop;

import java.util.ArrayList;

/**
 * 深拷贝
 * 
 * @author HeJW
 * 
 */
public class ShenClone implements Cloneable {

	private ArrayList<String> arrayList = new ArrayList<String>();

	@Override
	protected ShenClone clone() {

		ShenClone shen = null;
		try {
			shen = (ShenClone) super.clone();
			//比浅拷贝多了一句话。。。
			shen.arrayList = (ArrayList<String>)this.arrayList.clone();
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		return shen;
	}
	
	public void setValue( String value ){
		this.arrayList.add(value);
	}
	
	public ArrayList<String> getValue(){
		return this.arrayList;
	}
	
	public static void main(String[] args) {
		
		ShenClone shen = new ShenClone();
		shen.setValue("张三");
		
		ShenClone shenClone = shen.clone();
		shenClone.setValue("李四");
		
		System.out.println(shen.getValue());
	}

}

    这样运行后只有:

[张三]

源码:我的Git——https://github.com/hejiawang/DesignPattern

猜你喜欢

转载自hejiawangjava.iteye.com/blog/2244575