Java深克隆和浅克隆的原理及实现
2016-04-09 19:29
357 查看
Java中没有C++中所谓的拷贝构造函数,但是相应地提供了Cloneable接口。在Java中所有类都实现了clone()方法,因为Java中的所有类的父类Object具有clone()方法,而所有Java类都是Object类的子类。某个对象如果想要能够实现克隆,那么该对象的类必须实现cloneable接口。Cloneable接口仅仅只是一个标记接口,不包含任何需要实现的方法。如果某个对象的类没有实现Cloneable接口而调用clone()方法,那么会抛出CloneNotSupportedException。
什么叫浅克隆?什么叫深克隆?克隆就是指将值复制一份到新的对象中,而浅克隆就是对象的引用类型变量复制的是对象的引用值,深克隆就是将引用类型变量所指向的对象内存空间也复制一份给新对象。如下图所示。
如何实现对象的克隆?分三步:
对象的类实现Cloneable接口;
覆盖Object类的clone()方法;
在clone()方法中调用super.clone();
以上只是覆盖了Object类的clone()方法,默认的是浅克隆。String对象复制了其引用值,而不是复制了内存,否则sc1.name == sc2.name为false。
要想实现深克隆很简单,只要引用类型的成员变量所属类也实现Cloneable接口,在clone()方法里对该成员变量也调用它的clone()方法即可。
什么叫浅克隆?什么叫深克隆?克隆就是指将值复制一份到新的对象中,而浅克隆就是对象的引用类型变量复制的是对象的引用值,深克隆就是将引用类型变量所指向的对象内存空间也复制一份给新对象。如下图所示。
如何实现对象的克隆?分三步:
对象的类实现Cloneable接口;
覆盖Object类的clone()方法;
在clone()方法中调用super.clone();
public class ShallowClone implements Cloneable{ public int id; public String name; public ShallowClone(int id, String name){ this.id = id; this.name = name; } public Object clone(){ Object sc = null; try { sc = super.clone(); } catch (Exception e) { System.out.println(e.toString()); } return sc; } public static void main(String[] args) { // TODO Auto-generated method stub ShallowClone sc1 = new ShallowClone(1, "sc1Name"); ShallowClone sc2 = (ShallowClone)sc1.clone(); System.out.println("sc1's id: " + sc1.id + "\tsc2's id: " + sc2.id); System.out.println("sc1's name: " + sc1.name + "\tsc2's name: " + sc2.name); System.out.println(sc1.name == sc2.name); System.out.println(sc1.name.equals(sc2.name)); } }
输出结果:
sc1's id: 1 sc2's id: 1 sc1's name: sc1Name sc2's name: sc1Name true true
以上只是覆盖了Object类的clone()方法,默认的是浅克隆。String对象复制了其引用值,而不是复制了内存,否则sc1.name == sc2.name为false。
要想实现深克隆很简单,只要引用类型的成员变量所属类也实现Cloneable接口,在clone()方法里对该成员变量也调用它的clone()方法即可。
相关文章推荐
- 共同学习Java源码--常用数据类型--String(十一)
- 初识java
- 在Eclipse中,使用v7-recyclerview问题
- Java —— 表达式计算器
- 未重新服务器而导致的错误java.sql.SQLException: Parameter index out of range (1 > number of parameters, which is
- 文件传输基础——Java IO流
- 关于eclipse连接不到genymotion的问题,eclipsegenymotion
- Eclipse下开发Spark程序碰到的一个错误
- Java NIO(6)----NIO与IO
- Java NIO(5)----Pipe
- Java 笔记(1)
- Java NIO(4)----几种Channel
- Eclipse安装PyDev插件
- JVM-并发-Java 内存模型
- java毕向东听课笔记11(异常体系)
- RSA加解密算法java实现(已添加分段加密算法处理)
- Java实验2 类的继承性
- java.lang.ExceptionInInitializerError的原因
- Spring的Bean组件
- Java NIO(3)----Selector