摘要:為什么使用存在一個對象,已有初始值,這時候可能需要一個新的對象和相同,但是和是兩個獨立的對象,任意一個改動都不影響其中一個的值,但是的初始值由確定,這時候就是最有效也是最簡單的方法。
為什么使用clone
存在一個對象A,A已有初始值,這時候可能需要一個新的對象B和A相同,但是A和B是兩個獨立的對象,任意一個改動都不影響其中一個的值,但是B的初始值由A確定,這時候clone就是最有效也是最簡單的方法。
new一個對象和clone一個對象的區別new操作符的本意是分配內存空間,java程序執行到new操作符時,首先去看new操作符后面的類型,知道類型才能知道需要分配多大的內存空間,分配完成,調用構造函數,填充對象,完成對象的初始化。
clone的第一步也是分配內存,java程序執行到clone這一步時,分配的內存和調用clone方法的對象相同,在根據原對象完成對新對象的初始化,一個新的對象就被創建完成。
復制對象和克隆對象需要克隆的對象要繼承Cloneable接口,并重寫clone()方法
復制對象定義類:
public class People1 { private String name; private Integer age; public People1(String name, Integer age) { this.name = name; this.age = age; } }
復制測試
public class test { public static void main(String[] args) { People1 people1 = new People1("people",18); People1 people11 = people1; System.out.println(people1); System.out.println(people11); System.out.println(people1 == people11); } }
結果:
證明復制對象只是指向原來的對象,people1和people11只是引用同一個對象
clone對象定義類:
public class People2 implements Cloneable{ private String name; private Integer age; public People2(String name, Integer age) { this.name = name; this.age = age; } public String getName() { return name; } public Integer getAge() { return age; } public void setName(String name) { this.name = name; } public void setAge(Integer age) { this.age = age; } @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); } }
測試:
public class test { public static void main(String[] args) { //clone People2 people2 = new People2("people",18); People2 people22 = null; try { people22 = (People2) people2.clone(); } catch (CloneNotSupportedException e) { e.printStackTrace(); } System.out.println(people2); System.out.println(people22); System.out.println(people2 == people22); } }
結果:
可以看出people2和people22指向的對象并不是同一個的
定義類:
Student類:
public class Student implements Cloneable{ private String name; private Integer age; private Teacher teacher; public Student(String name, Integer age,Teacher teacher) { this.name = name; this.age = age; this.teacher = teacher; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } public Teacher getTeacher() { return teacher; } public void setTeacher(Teacher teacher) { this.teacher = teacher; } @Override public String toString() { return "學生: name=" + name + ", age=" + age + ",指導" + teacher; } @Override protected Object clone() throws CloneNotSupportedException { return super.clone(); } }
Teacher類
public class Teacher { private String name; private Integer age; public Teacher(String name, Integer age) { this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } @Override public String toString() { return "老師:name=" + name + ", age=" + age ; } }淺克隆
main函數
public class test2 { public static void main(String[] args) { Teacher teacher = new Teacher("劉老師",18); Student student1 = new Student("小明",10,teacher); Student student2 = null; try { student2 = (Student) student1.clone(); } catch (CloneNotSupportedException e) { e.printStackTrace(); } Teacher t1 = student2.getTeacher(); t1.setName("張老師"); t1.setAge(30); student2.setName("小紅"); student2.setAge(9); student2.setTeacher(t1); System.out.println(student1); System.out.println(student2); } }
結果:
修改student2中的Teacher類,student1也跟著改變,而修改姓名和年齡并不會修改,由此得出才重新clone方法時不能直接super
Teacher繼承Cloneable
Student重寫clone方法
Student newStudent = (Student) super.clone(); newStudent.teacher = (Teacher) teacher.clone(); return newStudent;
運行上方測試代碼,結果:
完成預想結果
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/75469.html
摘要:優點簡單易實現缺點無法真正克隆對象深克隆實現通過遞歸克隆實現代碼輸出通過序列化實現代碼輸出結果分析采用深克隆能有效隔離源對象與克隆對象的聯系。 本文首發于cartoon的博客 ????轉載請注明出處:https://cartoonyu.github.io/cartoon-blog/post/java/java%E5%AE%9E%E7%8E%B0%E5%85%8B%E9%9A%86%E...
摘要:淺拷貝與深拷貝一數據類型數據分為基本數據類型,和對象數據類型。淺拷貝是按位拷貝對象,它會創建一個新對象,這個對象有著原始對象屬性值的一份精確拷貝。對于字符串數字及布爾值來說不是或者對象,會拷貝這些值到新的數組里。 淺拷貝與深拷貝 一、數據類型數據分為基本數據類型(String, Number, Boolean, Null, Undefined,Symbol)和對象數據類型。 基本數據類...
摘要:引用類型值引用類型值是保存在堆內存中的對象,變量保存的只是指向該內存的地址,在復制引用類型值的時候,其實只復制了指向該內存的地址。 前言 要理解 JavaScript中淺拷貝和深拷貝的區別,首先要明白JavaScript的數據類型。JavaScript有兩種數據類型,基礎數據類型和引用數據類型。js的基本類型:undefined,null,string,boolean,number,s...
閱讀 3925·2021-10-12 10:12
閱讀 2886·2021-09-10 11:18
閱讀 3673·2019-08-30 15:54
閱讀 2808·2019-08-30 15:53
閱讀 638·2019-08-30 13:54
閱讀 965·2019-08-30 13:21
閱讀 2260·2019-08-30 12:57
閱讀 1687·2019-08-30 11:10