-- 在创建对象原型时,继承该基类的基本结构和所有数据
-- 注意:深度克隆和浅度克隆 (区分 引用和基本数据类型)
*实现Cloneable接口:与Serializable接口一样,作为标识
实现Cloneable接口 重写java.lang.Object的clone成员方法。
--浅度克隆
缺点: 当有引用数据类型(类,枚举,数组,集合List、Map等)时会复制同一份内存地址
package com.prototype;
import java.util.List;
/**
* @description: 原型模式-浅度克隆
* @author: ziHeng
* @create: 2018-08-04 19:13
**/
public class ShallowClone implements Cloneable{
private String name;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public ShallowClone clone(){
try {
return (ShallowClone) super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
return null;
}
}
}
--深度克隆(解决引用类型地址相同的问题)
栗子里添加了List<String> friends 的引用类型
解决原理: new一个新的引用类型,并赋值原有的数据进去
package com.prototype;
import java.util.ArrayList;
import java.util.List;
/**
* @description: 原型模式-深度克隆
* @author: ziHeng
* @create: 2018-08-04 19:13
**/
public class DepthClone implements Cloneable{
private String name;
private int age;
//添加了引用数据类型
private List<String> friends;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public List<String> getFriends() {
return friends;
}
public void setFriends(List<String> friends) {
this.friends = friends;
}
@Override
public DepthClone clone(){
try {
//用下列几行代码解决,觉得死板的可用反射
DepthClone depthClone = (DepthClone) super.clone();
//新的内存实例
List<String> newFriends = new ArrayList<>();
//读取被克隆类的数据
//newFriends.addAll(this.friends);
for(String friend:this.friends){
newFriends.add(friend);
}
depthClone.setFriends(newFriends);
return depthClone;
} catch (CloneNotSupportedException e) {
e.printStackTrace();
return null;
}
}
}