博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
java浅拷贝(shallow clone)与深拷贝(deep clone)
阅读量:4290 次
发布时间:2019-05-27

本文共 2570 字,大约阅读时间需要 8 分钟。

浅复制与深复制概念


浅复制

被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用仍然指向原来的对象。换言之,浅复制仅仅复制所考虑的对象,而不复制它所引用的对象。

深复制

被复制对象的所有变量都含有与原来的对象相同的值,除去那些引用其他对象的变量。那些引用其他对象的变量将指向被复制过的新对象,而不再是原有的那些被引用的对象。换言之,深复制把要复制的对象所引用的对象都复制了一遍。

浅复制的实现:

public static void main(String[] args) throws CloneNotSupportedException {    Teacher teacher = new Teacher();    teacher.setAge(20);    teacher.setName("zhangsan");    Student2 s1 = new Student2();    s1.setAge(21);    s1.setName("lisi");    s1.setTeacher(teacher);    Student2 s2 = (Student2) s1.clone();    System.out.println(s2.getName());    System.out.println(s2.getAge());    teacher.setName("Teacher wang");    System.out.println(s2.getTeacher().getAge());    System.out.println(s2.getTeacher().getName());  }}class Teacher implements Cloneable {  private int age;  private String name;  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;  }}class Student2 implements Cloneable {  private int age;  private String name;  private Teacher teacher;  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;  }  public Teacher getTeacher() {    return teacher;  }  public void setTeacher(Teacher teacher) {    this.teacher = teacher;  }  @Override  public Object clone() throws CloneNotSupportedException {    return super.clone();  }

输出结果:

lisi2120Teacher wang

对上述浅复制进行一定的修改让变成深复制:

对Teacher类也重写clone方法:

class Teacher implements Cloneable {  ...  @Override  public Object clone() throws CloneNotSupportedException {    return super.clone();  }  ...}

修改Student2类的clone实现:

...@Override  public Object clone() throws CloneNotSupportedException {    Student2 student2 = (Student2) super.clone();    student2.setTeacher((Teacher)student2.getTeacher().clone());    return student2;  }...

返回的结果:

lisi2120zhangsan

这种方式可以做到深复制的需求,但是如果有错综复杂的对象引用,显然这种方式是不可取的,下面我们用序列化的方式来实现深复制:

把对象写到流里的过程是序列化(Serilization)过程,而把对象从流中读出来的过程则叫做反序列化(Deserialization)过程。应当指出的是,写在流里的对象是一个拷贝,而原对象仍然存在于JVM里面。

在Student类中添加序列化的方法:

...public Object deepCopy() throws IOException, ClassNotFoundException {    ByteArrayOutputStream bos = new ByteArrayOutputStream();    ObjectOutputStream oos = new ObjectOutputStream(bos);    oos.writeObject(this);    ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray());    ObjectInputStream ois = new ObjectInputStream(bis);    return ois.readObject();  } ...

转载地址:http://emrgi.baihongyu.com/

你可能感兴趣的文章
面试神器第二弹:Rxjava熟悉——操作符
查看>>
带你过一遍Android 多主题框架——MagicaSakura
查看>>
这款神器你不学就要落后了!
查看>>
谷歌开源跨平台UI框架——Flutter
查看>>
Android进阶必学:自定义注解之动态代理
查看>>
Android进阶必学:自定义注解之反射
查看>>
Android进阶之注解解析和自定义注解
查看>>
你想成为Android高级工程师你还得学习Hook
查看>>
菜鸟带你Hook技术实战
查看>>
BAT面试题集锦——Java基础(一)
查看>>
BAT面试题集锦——Java基础(二)
查看>>
Retrofit原理解析最简洁的思路
查看>>
Okhttp的源码解读
查看>>
【Android P】 JobScheduler服务源码解析(二) ——框架解析
查看>>
【Android P】 JobScheduler服务源码解析(三)—— 使用Job需要注意的点
查看>>
string和wstring相互转换
查看>>
c++读取utf8等不同编码文件
查看>>
STL中的vector
查看>>
C++中的map
查看>>
Python小时钟
查看>>