1 import java.io.Serializable; 2 import java.util.ArrayList; 3 import java.util.List; 4 5 import cn.hutool.core.clone.CloneRuntimeException; 6 import cn.hutool.core.clone.Cloneable; 7 import cn.hutool.core.util.ObjectUtil; 8 9 abstract class Pet implements Serializable { 10 private static final long serialVersionUID = 6949926634898983095L; 11 protected String name; 12 13 public Pet() { 14 super(); 15 } 16 public Pet(String name) { 17 super(); 18 this.name = name; 19 } 20 @Override 21 public int hashCode() { 22 final int prime = 31; 23 int result = 1; 24 result = prime * result + ((name == null) ? 0 : name.hashCode()); 25 return result; 26 } 27 @Override 28 public boolean equals(Object obj) { 29 if (this == obj) 30 return true; 31 if (obj == null) 32 return false; 33 if (getClass() != obj.getClass()) 34 return false; 35 Pet other = (Pet) obj; 36 if (name == null) { 37 if (other.name != null) 38 return false; 39 } else if (!name.equals(other.name)) 40 return false; 41 return true; 42 } 43 } 44 45 class Dog extends Pet { 46 private static final long serialVersionUID = 5872302442689438099L; 47 48 public Dog() { 49 super(); 50 } 51 public Dog(String name) { 52 super(name); 53 } 54 public void bark () { 55 System.out.print(name + "犬吠"); 56 } 57 @Override 58 public String toString() { 59 return "Dog [name=" + name + "]"; 60 } 61 } 62 63 class Student implements Cloneable<Student>, Serializable{ 64 private static final long serialVersionUID = -7925019110753655045L; 65 66 private String name; 67 private int age; 68 private List<Pet> pets; 69 public Student() { 70 super(); 71 } 72 public String getName() { 73 return name; 74 } 75 public void setName(String name) { 76 this.name = name; 77 } 78 public int getAge() { 79 return age; 80 } 81 public void setAge(int age) { 82 this.age = age; 83 } 84 public List<Pet> getPets() { 85 return pets; 86 } 87 public void setPets(List<Pet> pets) { 88 this.pets = pets; 89 } 90 @Override 91 public String toString() { 92 return "Student [name=" + name + ", age=" + age + ", pets=" + pets 93 + "]"; 94 } 95 @Override 96 public Student clone() { 97 try { 98 Student student = (Student)super.clone(); 99 return student; 100 } catch (CloneNotSupportedException e) { 101 throw new CloneRuntimeException(e); 102 } 103 } 104 @Override 105 public int hashCode() { 106 final int prime = 31; 107 int result = 1; 108 result = prime * result + age; 109 result = prime * result + ((name == null) ? 0 : name.hashCode()); 110 result = prime * result + ((pets == null) ? 0 : pets.hashCode()); 111 return result; 112 } 113 @Override 114 public boolean equals(Object obj) { 115 if (this == obj) 116 return true; 117 if (obj == null) 118 return false; 119 if (getClass() != obj.getClass()) 120 return false; 121 Student other = (Student) obj; 122 if (age != other.age) 123 return false; 124 if (name == null) { 125 if (other.name != null) 126 return false; 127 } else if (!name.equals(other.name)) 128 return false; 129 if (pets == null) { 130 if (other.pets != null) 131 return false; 132 } else if (!pets.equals(other.pets)) 133 return false; 134 return true; 135 } 136 } 137 138 public class CloneTest { 139 public static void main(String[] args) { 140 List<Pet> pets = new ArrayList<>(); 141 pets.add(new Dog("柯基")); 142 143 Student s1 = new Student(); 144 s1.setName("小明"); 145 s1.setAge(12); 146 s1.setPets(pets); 147 148 Student s2 = s1.clone(); // 浅克隆 149 Student s3 = ObjectUtil.cloneByStream(s1); // 深克隆,注意:执行深克隆时,该类以及该类的成员变量所属的类都需要实现Serializable接口 150 Student s4 = ObjectUtil.clone(s1); // 当克隆的对象所属的类实现了Cloneable接口后,执行浅克隆,否则执行深克隆 151 // System.out.println(s1 == s2); 152 // System.out.println(s1.equals(s2)); 153 // System.out.println(s1 == s3); 154 // System.out.println(s1.equals(s3)); 155 // System.out.println(s1 == s4); 156 // System.out.println(s1.equals(s4)); 157 158 System.out.println(s1.getPets() == s4.getPets()); // true 159 System.out.println(s1.getPets() == s3.getPets()); // false 160 System.out.println(s1.equals(s3)); // true 161 // System.out.println(s2); 162 System.out.println(s3); 163 // System.out.println(s4); 164 } 165 }