大话设计模式--原型模式

  在一些情景下面,会需要把一些重复的资料如 简历,模板等进行复制使用,所以要是手动就太麻烦了,所以在java代码设计中就有了原型模式,即克隆模式。

      每个需要克隆的类都要有一个Clone方法,并且实现Cloneable接口,不然会报CloneNotSupportedException这个异常。   

  原型模式有两种状态:浅复制与深复制。

   浅复制:调用的是原类型的内存地址,其实跟原先的类一样。


   深复制:复制原先的数据,并且在内存中重新开辟一块内存空间,即一个新的对象。

    例子如下:

package effective.yuanxing;

public class WorkExperience implements Cloneable {
	private String workDate;
	public String WorkDate;
	private String company;
	public  String Company;
	public String getWorkDate() {
		return workDate;
	}
	public void setWorkDate(String workDate) {
		this.workDate = workDate;
	}
	public String getCompany() {
		return company;
	}
	public void setCompany(String company) {
		this.company = company;
	}
	public Object Clone(){
		Object obj = null;
		try {
			obj = super.clone();
			return obj;
		} catch (CloneNotSupportedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
			System.out.println("不支持克隆");
			return null ;
		}
	}

}

浅克隆:

package effective.yuanxing;

public class Resume implements Cloneable{

	private String name;
	private String sex;
	private String age;
	
	private WorkExperience work;
	
	public Resume(String name ){
		this.name = name;
		work = new WorkExperience();
	}
	//设置个人信息
	public void SetPersonalInfo(String sex , String age){
		this.sex = sex;
		this.age = age;
	}
	//设置工作经历
	public void SetWorkExperoence(String workDate , String company){
		work.WorkDate = workDate;
		work.Company = company;
	}
	//显示
	public void Display(){
		System.out.println("name:"+name +"sex:"+sex+"age: "+age);
		System.out.println("工作经历:"+work.WorkDate+work.Company);
	}
	public Object Clone(){
		try {
			return (Object)super.clone();
		} catch (CloneNotSupportedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
			return null;
		}
	}
	public static void main(String[] args) {
		Resume a = new Resume("大鸟");
		a.SetPersonalInfo("男", "29");
		a.SetWorkExperoence("2015-2018", "XX公司");
		Resume b =(Resume)a.Clone();
		b.SetPersonalInfo("2016-2018", "yy企业");
		Resume c =(Resume)a.Clone();
		c.SetPersonalInfo("男", "24");
		c.SetWorkExperoence("1998-2003", "zo企业");
		
		a.Display();
		b.Display();
		c.Display();
                System.out.println(a.work==b.work);
		System.out.println(a.work.Company);
	}
}
结果:
name:大鸟sex:男age: 29
工作经历:1998-2003zo企业
name:大鸟sex:2016-2018age: yy企业
工作经历:1998-2003zo企业
name:大鸟sex:男age: 24
工作经历:1998-2003zo企业
true
zo企业

可见浅复制的 work对象为同一个对象。并且原来的Company也会被修改,即访问的是原来的对象。

深复制:

package effective.yuanxing;

public class DeepResume {

	private String name;
	private String sex;
	private String age;
	
	private WorkExperience work;
	
	public DeepResume(String name ){
		this.name = name;
		work = new WorkExperience();
	}
	public DeepResume(WorkExperience work){
		this.work = (WorkExperience)work.Clone();
	}
	//设置个人信息
	public void SetPersonalInfo(String sex , String age){
		this.sex = sex;
		this.age = age;
	}
	//设置工作经历
	public void SetWorkExperoence(String workDate , String company){
		work.WorkDate = workDate;
		work.Company = company;
	}
	//显示
	public void Display(){
		System.out.println("name:"+name +"sex:"+sex+"age: "+age);
	}
	public Object Clone(){
		DeepResume obj = new DeepResume(this.work);
		obj.name = this.name;
		obj.sex = this.sex;
		obj.age = this.age;
		return obj;
	}
	public static void main(String[] args) {
		DeepResume a = new DeepResume("大鸟");
		a.SetPersonalInfo("男", "29");
		a.SetWorkExperoence("2015-2018", "XX公司");
		DeepResume b =(DeepResume)a.Clone();
		b.SetPersonalInfo("2016-2018", "yy企业");
		DeepResume c =(DeepResume)a.Clone();
		c.SetPersonalInfo("男", "24");
		c.SetWorkExperoence("1998-2003", "zz企业");
		
		a.Display();
		b.Display();
		c.Display();
		System.out.println(b.work==c.work);
		System.out.println(a.work.Company);
	}
}

结果:

name:大鸟sex:男age: 29
name:大鸟sex:2016-2018age: yy企业
name:大鸟sex:男age: 24
false
XX公司

可见它们的work对象重新创建。

应用场景:类似一个像下围棋 五子棋时,创建棋子的时候就可以用原型模式创建旗子

猜你喜欢

转载自blog.csdn.net/qq_27098879/article/details/80034716
今日推荐