一、基础回忆
1、先来回忆一下建立对象的副本
public class Test {
public static void main(String[] args) {
//初始化一个对象
Hello h = new Hello(2);
//输出一下它的值
System.out.println(h.getA());
//实例化一个对象指向 = h
Hello h1 = h;
//到修改h1的对象值
h1.setA(3);
System.out.println(h.getA());
}
}
class Hello {
private int a;
public Hello() {
}
public int getA() {
return a;
}
public void setA(int a) {
this.a = a;
}
public Hello(int a) {
this.a = a;
}
}
- 不难发现我们的实例化的h1其实是指向了h的实例化对象
2、我们来调用一下Clone方法试一下
为了方便查看书:把Hello名改为Employee 类
public class Test {
public static void main(String[] args) throws CloneNotSupportedException {
//初始化一个对象
Employee original = new Employee(2);
//输出一下它的值
System.out.println(h.getA());
//调用clone方法
Employee copy= h.clone();
}
}
class Employee implements Cloneable {
private int a;
public Employee() {
}
public int getA() {
return a;
}
public void setA(int a) {
this.a = a;
}
public Employee(int a) {
this.a = a;
}
//记得我这修改了一下访问符
@Override
public Employee clone() throws CloneNotSupportedException {
return (Employee)super.clone();
}
}
3、看一下clone()方法
首先去看一下我们的源代码
- 方法是我们的protected定义的,你的代码不能直接去调用,只能子类和本包的调用,必须去实现这个方法才可以【强制转型一下】。【这就是继承设计的巧妙之处了】
- 要想调用我们的clone()方法必须去实现Cloneable接口。
- 方法实现的浅拷贝
在我们上面的第二步的实现其实完全没有问题,你拷贝就完全拷贝过去,我们的copy对象就在堆内存重新划分到了一块内存空间,在你的项目里面也完全没什么问题。但是,但是,但是,请看下面的分析
4、来看一下我们的浅拷贝和深拷贝
(1)浅拷贝
- 我们对象original和copy对象里面的属性时如下的情况
- 如果是基本数据类型:直接复制
- 如果是应用类型:直接复制它的引用
(2)深拷贝
- 深拷贝和浅拷贝是对应的
- 如果是基本数据类型:直接复制
- 如果是应用类型:也要重新进行拷贝
5、怎么实现深拷贝
答案是在实现我们的clone方法的时候进行设置