前言:
我们经常会遇到某个已有对象A,创建出另外一个与A具有相同状态的对象B,并且对B的修改不会影响A的状态,这就需要clone一个对象实例。在Java语言中简单的复制操作无法达到这个目的(对象的赋值属于引用传递,传递的是地址),而Java提供clone方法解决这个问题。
步骤:
1.继承Cloneable接口(Cloneable是标识接口,没有任何方法)
2.在类中重写Object类中的clone方法
3.在clone方法中调用super.clone()方法
4.把浅复制的引用对象指向原型对象的新克隆体
克隆类:
public class cloneClass implements Cloneable{ //1.继承Cloneable接口 private int anInt=0; public int getAnInt() { return anInt; } public void setAnInt(int anInt) { this.anInt = anInt; } public void changeInt(){ this.anInt=1; } public Object clone(){ //2.在类中重写Object类中的clone方法 cloneClass o = null; try { o=(cloneClass)super.clone();//3.在clone方法中调用super.clone()方法 } catch (CloneNotSupportedException e) { e.printStackTrace(); } return o; } }
测试类:
class test{
public static void main(String[] args) {
cloneClass a = new cloneClass();
cloneClass b = (cloneClass) a.clone(); //4.把浅复制的引用对象指向原型对象的新克隆体
//原始 a b的值
System.out.println("a:"+a.getAnInt());
System.out.println("b:"+b.getAnInt());
b.changeInt();
//克隆之后
System.out.println("a:"+a.getAnInt());
System.out.println("b:"+b.getAnInt());
}
}
程序运行结果
a:0
b:0
a:0
扫描二维码关注公众号,回复:
518167 查看本文章
b:1
对象b调用函数changeInt函数,改变了b的anInt的值,而对象a的anInt值并未改变。这就是clone的功能。
深复制与浅复制
在类中只有一些基本的数据类型的时候,采用上述的方法就可以了,但是类中包含对象时就要用到深复制。实现的方法是在对对象调用clone()方法完成复制之后,接着对对象中的非基本类型的属性也调用clone()方法完成深复制。
import java.util.Date; class deepclone implements Cloneable{ private Date birth = new Date(); public Date getBirth(){ return birth; } public void setBirth(){ this.birth=birth; } public void changeDate(){ this.birth.setMonth(0); } public Object clone(){ deepclone d=null; try { d = (deepclone)super.clone(); } catch (CloneNotSupportedException e) { e.printStackTrace(); } d.birth=(Date)this.getBirth().clone(); //对对象中的非基本类型的属性也调用clone()方法完成深复制 return d; } } class TestRef{ public static void main(String[] args) { deepclone a = new deepclone(); deepclone b = new deepclone(); System.out.println("b改变之前"); System.out.println("a="+a.getBirth()); System.out.println("b="+b.getBirth()); b.changeDate(); System.out.println("b改变之后"); System.out.println("a="+a.getBirth()); System.out.println("b="+b.getBirth()); } }
----------------------------------------------------------------------------------------------------------------------------------参考《Java程序员面试笔试宝典》