1. 程式人生 > >java中原型模式

java中原型模式

原型模式

1.過程相同,但結果不一樣。2.資料內容完全一樣,但例項不同(比如java中的clone。不走構造方法,直接copy位元組碼,生成一個新的物件

淺克隆

package com.gupaoedu.vip.prototype.simple;

import java.util.ArrayList;

public class ConcretePrototype implements Cloneable{

	private int age;

	private String name;
	
	public ArrayList<String> list = new ArrayList<String>();
	
	protected Object clone() throws CloneNotSupportedException {
		ConcretePrototype prototype = null;
		try{
			prototype = (ConcretePrototype)super.clone();
			prototype.list = (ArrayList)list.clone();
			
			//克隆基於位元組碼的
			//用反射,或者迴圈
		}catch(Exception e){
			
		}
		
		return prototype;
	}

	
	//定義上100個屬性
	
	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	
	
	
	
}
package com.gupaoedu.vip.prototype.simple;

import java.util.ArrayList;
import java.util.List;

public class CloneTest {

	
	
	public static void main(String[] args) {
		
		ConcretePrototype cp = new ConcretePrototype();
		cp.setAge(18);
		cp.setName("Tom");
		
		//cp.list.add("Tom");
		
		try {
			ConcretePrototype copy = (ConcretePrototype)cp.clone();
			
			System.out.println(copy.list  == cp.list);
			System.out.println(copy.getAge() + "," + copy.getName() + copy.list.size());
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		
		//就是一個現成的物件,這個物件裡面有已經設定好的值
		//當我要新建一個物件,並且要給新建的物件賦值,而且賦值內容要跟之前的一模一樣
		
		
		//ConcretePrototype cp = new ConcretePrototype();
		//cp.setAge(18);
		
		//ConcretePrototype copy = new ConcretePrototype();
		//copy.setAge(cp.getAge());
		//copy.setName(cp.getName());
		//用迴圈,用反射,確實可以的(反射效能並不高)
		//位元組碼複製newInstance()
		
		//ConcretePrototype copy = cp;
		//ORM的時候經常用到的
		
		
		//能夠直接拷貝其實際內容的資料型別/只支援9種,八大基本資料型別+String 淺拷貝
		//深拷貝
	}
	
}

深克隆

package com.gupaoedu.vip.prototype.greatestsage;

import java.util.Date;


//猴子
public class Monkey {
	//身高
	protected int height;//基本
	//體重
	protected int weight;
	//生日
	protected Date birthday;//不是基本型別
	
	public int getHeight() {
		return height;
	}
	public void setHeight(int height) {
		this.height = height;
	}
	public int getWeight() {
		return weight;
	}
	public void setWeight(int weight) {
		this.weight = weight;
	}
	public Date getBirthday() {
		return birthday;
	}
	public void setBirthday(Date birthday) {
		this.birthday = birthday;
	}


	
	
}
package com.gupaoedu.vip.prototype.greatestsage;

import java.io.Serializable;

/**
 * 金箍棒
 * @author Tom
 *
 */
public class GoldRingedStaff implements Serializable{
	
	private float height = 100; //長度
	private float diameter = 10;//直徑
	
	
	
	/**
	 * 金箍棒長大
	 */
	public void grow(){
		this.diameter *= 2;
		this.height *= 2;
	}
	
	/**
	 * 金箍棒縮小
	 */
	public void shrink(){
		this.diameter /= 2;
		this.height /= 2;
	}
	
}
package com.gupaoedu.vip.prototype.greatestsage;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.Date;

/**
 * 齊天大聖
 * @author Tom
 *
 */
public class TheGreatestSage  extends Monkey implements Cloneable,Serializable{
	
	//金箍棒
	private GoldRingedStaff staff;
	
	//從石頭縫裡蹦出來
	public TheGreatestSage(){
		this.staff = new GoldRingedStaff();
		this.birthday = new Date();
		this.height = 150;
		this.weight = 30;
		System.out.println("------------------------");
	}
	
	//分身技能
	public Object clone(){
		//深度克隆
		ByteArrayOutputStream bos = null;
		ObjectOutputStream oos = null;
		ByteArrayInputStream bis = null;
		ObjectInputStream ois = null;
		try {
			//return super.clone();//預設淺克隆,只克隆八大基本資料型別和String
			//序列化
			bos = new ByteArrayOutputStream();
			oos = new ObjectOutputStream(bos);
			oos.writeObject(this);
			
			//反序列化
			bis = new ByteArrayInputStream(bos.toByteArray());
			ois = new ObjectInputStream(bis);
			TheGreatestSage copy = (TheGreatestSage)ois.readObject();
			copy.birthday = new Date();
			
			return copy;
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}finally{
			try {
				bos.close();
				oos.close();
				bis.close();
				ois.close();
				
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	//變化
	public void change(){
		TheGreatestSage copySage = (TheGreatestSage)clone();
		System.out.println("大聖本尊生日是:" + this.getBirthday().getTime());
		System.out.println("克隆大聖的生日是:" + copySage.getBirthday().getTime());
		System.out.println("大聖本尊和克隆大聖是否為同一個物件:" + (this == copySage));
		System.out.println("大聖本尊持有的金箍棒跟克隆大聖持有金箍棒是否為同一個物件:" + (this.getStaff() == copySage.getStaff()));
	}
	
	public GoldRingedStaff getStaff() {
		return staff;
	}

	public void setStaff(GoldRingedStaff staff) {
		this.staff = staff;
	}
	
	
	
	
}
package com.gupaoedu.vip.prototype.greatestsage;


public class TestPrototype {
	public static void main(String[] args) {
		TheGreatestSage sage = new TheGreatestSage();
		sage.change();
		
		//跟《西遊記》中描述的一致,怎麼辦?
	}
}