克隆和赋值
- 克隆的结果是有多个相同的实体,各个对象指向不同的实体
- 而多个不同对象指向一个相同的实体不是克隆,而是赋值
clone
方法,需要满足: clone
方法,返回 super.clone()
Object
类是所有类的父类,但它内部的 clone
方法是 protected
修饰的,只有在同包中才能访问,所以需要在新包中重写 clone
方法return super.clone()
的意思就是调用父类(Object类)中的 clone
方法clone
方法的对象 clone
方法后的返回类型是 Object
类,而调用 clone
方法的对象是 Student
类Object
需要强制类型转换成子类Student
CloneNotSuppertedException
异常Clonable
接口 class Student implements Cloneable{ public int age = 10; @Override //重写clone方法 protected Object clone() throws CloneNotSupportedException { return super.clone(); } } public class Test { public static void main(String[] args) throws CloneNotSupportedException { Student student1 = new Student(); Student student2 = (Student)student1.clone(); System.out.println(student1.age); //输出:10 System.out.println(student2.age); //输出:10 } }
class Money { public double money = 12.5; } class Student implements Cloneable{ public int age = 10; public Money m = new Money(); @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); } } public class Test { public static void main(String[] args) throws CloneNotSupportedException { Student student1 = new Student(); Student student2 = (Student)student1.clone(); System.out.println(student1.m.money); //输出:12.5 System.out.println(student2.m.money); //输出:12.5 System.out.println("========="); student1.m.money = 100; System.out.println(student1.m.money); //输出:100 System.out.println(student2.m.money); //输出:100 } }
观察输出结果可以发现:
- 将 student1 指向的对象m中的 money 成员改变后,student2 指向的对象中的 money 成员的值也变成了相同的值
所以可知:
- student1 和 student2 指向的 m 对象所指向的 money 成员是一样的
若想在当 student1 修改 money 的值的时候,student2 中的 money 的值不变,就需要使用深克隆了
student1
对象 age = 10
和 m
这两个数据 m
是指向 Money
对象的指针或引用,这个 Money
对象里面有一个 money = 12.5
字段clone
方法 student1
一模一样的内容tmp
tmp
指向新克隆出来的内容的地址Money
Money
类要支持 clone
方法 Clonable
接口clone
方法tmp
中的 m
tmp
tmp
的指向地址赋值给 student2
,克隆完成class Money implements Cloneable{ public double money = 12.5; @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); } } class Student implements Cloneable{ public int age = 10; public Money m = new Money(); @Override protected Object clone() throws CloneNotSupportedException { Student tmp = (Student) super.clone(); tmp.m = (Money)this.m.clone(); return tmp; } } public class Test { public static void main(String[] args) throws CloneNotSupportedException { Student student1 = new Student(); Student student2 = (Student)student1.clone(); System.out.println(student1.m.money); //输出:12.5 System.out.println(student2.m.money); //输出:12.5 System.out.println("========="); student1.m.money = 100; System.out.println(student1.m.money); //输出:100 System.out.println(student2.m.money); //输出:12.5 } }