深拷贝和浅拷贝的区别
- 浅拷贝:对于对象内的引用数据类型,浅拷贝会直接复制其对象的地址,也就是拷贝对象和原对象公用一个内部对象。
- 深拷贝:会完全复制整个对象,包括对象所包含的内部对象,都是新创建的对象。
浅拷贝
浅拷贝的示例代码如下,我们这里实现了 Cloneable
接口,并重写了 clone()
方法。
clone()
方法的实现很简单,直接调用的是父类 Object
的 clone()
方法。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| public class Address implements Cloneable{ private String name; @Override public Address clone() { try { return (Address) super.clone(); } catch (CloneNotSupportedException e) { throw new AssertionError(); } } }
public class Person implements Cloneable { private Address address; @Override public Person clone() { try { Person person = (Person) super.clone(); return person; } catch (CloneNotSupportedException e) { throw new AssertionError(); } } }
|
测试:
1 2 3 4
| Person person1 = new Person(new Address("武汉")); Person person1Copy = person1.clone();
System.out.println(person1.getAddress() == person1Copy.getAddress());
|
从输出结构就可以看出, person1
的克隆对象和 person1
使用的仍然是同一个 Address
对象。
深拷贝
这里我们简单对 Person
类的 clone()
方法进行修改,连带着要把 Person
对象内部的 Address
对象一起复制。
1 2 3 4 5 6 7 8 9 10
| @Override public Person clone() { try { Person person = (Person) super.clone(); person.setAddress(person.getAddress().clone()); return person; } catch (CloneNotSupportedException e) { throw new AssertionError(); } }
|
测试:
1 2 3 4
| Person person1 = new Person(new Address("武汉")); Person person1Copy = person1.clone();
System.out.println(person1.getAddress() == person1Copy.getAddress());
|
从输出结构就可以看出,显然 person1
的克隆对象和 person1
包含的 Address
对象已经是不同的了。
那什么是引用拷贝呢? 简单来说,引用拷贝就是两个不同的引用指向同一个对象。
参考:JavaGuide