Interface clonable :
La classe qui implémente cette interface - on peut en déduire que la méthode clone() peut être légalement appelée - pour implémenter des instances de classe : attribut à attribut copier. java.lang.Object
les sous-classes qui implémentent l'interface Cloneable doivent remplacer la méthode clone() avec un accès public (bien que la méthode clone dans la classe java.Object soit de type protégé)
Il faut comprendre que l'interface Cloneable ne incluez la méthode clone(), par conséquent, si vous implémentez simplement l'interface Cloneable, vous ne pourrez pas cloner l'objet normalement[Raison : même si la méthode clone est appelée de manière réfléchie, il n'y a aucune garantie qu'elle réussira]&mdash ;—Personnel La compréhension est la suivante :Cela est dû au fait de savoir s'il faut remplacer la méthode Clone() ou au problème de "copie superficielle et copie profonde".
class Pet implements Cloneable{ //properties private String name; public void setName(String name) { this.name = name; } public String getName() { return name; } public Pet() { } public Pet(String name) { this.name = name; } @Override public String toString() { return "Pet{" + "name='" + name + '\'' + '}'; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; Pet pet = (Pet) o; return Objects.equals(name, pet.name); } @Override public int hashCode() { return Objects.hash(name); } // @Override // public Pet clone() { // try { // return (Pet)super.clone(); // } catch (CloneNotSupportedException e) { // e.printStackTrace(); // } // return null; // } }Cas de copie superficielleDéfinition de la classe PetRemarque : la classe Pet implémente l'interface Cloneable, mais ne remplace pas la méthode Clone() (évidemment : la classe Pet n'a pas la possibilité de cloner des objets pour le moment ).
class Pet implements Cloneable{ //properties private String name; public void setName(String name) { this.name = name; } public String getName() { return name; } public Pet() { } public Pet(String name) { this.name = name; } @Override public String toString() { return "Pet{" + "name='" + name + '\'' + '}'; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; Pet pet = (Pet) o; return Objects.equals(name, pet.name); } @Override public int hashCode() { return Objects.hash(name); } // @Override // public Pet clone() { // try { // return (Pet)super.clone(); // } catch (CloneNotSupportedException e) { // e.printStackTrace(); // } // return null; // } }Définition de la classe PersonRemarque : La classe Person implémente l'interface Cloneable et remplace également la méthode Clone(). Alors, la classe Person a-t-elle la capacité de cloner des objets ? (En raison du problème de copie superficielle, cette capacité de clonage d'objet est considérée comme incomplète et défectueuse).
class Pet implements Cloneable{ //properties private String name; public void setName(String name) { this.name = name; } public String getName() { return name; } public Pet() { } public Pet(String name) { this.name = name; } @Override public String toString() { return "Pet{" + "name='" + name + '\'' + '}'; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; Pet pet = (Pet) o; return Objects.equals(name, pet.name); } @Override public int hashCode() { return Objects.hash(name); } // @Override // public Pet clone() { // try { // return (Pet)super.clone(); // } catch (CloneNotSupportedException e) { // e.printStackTrace(); // } // return null; // } }Problème de copie superficielle - test de codePourquoi est-il dit : La capacité de clonage d'objets de la classe Person est incomplète et défectueuse pour le moment ? Car à ce stade, lorsque la méthode clone() est appelée via l'objet Person et que l'objet est cloné, le clone de la valeur de son attribut membre pet (un objet de la classe Pet) n'est qu'une simple copie de l'adresse mémoire dans la zone du tas. C'est-à-dire : pour parler franchement, la valeur de l'attribut pet de l'objet Person et l'objet cloné partagent la même zone de mémoire de tas. Le problème est évident : lorsque l'attribut pet de l'objet cloné est défini, cela affectera évidemment la valeur de l'attribut pet de l'objet Person d'origine.
La démonstration du code est la suivante :
//methods public static void main(String[] args) throws CloneNotSupportedException { testPerson(); } public static void testPerson() throws CloneNotSupportedException { Person p=new Person("张三",14,new Pet("小黑")); System.out.println(p); Person clone = (Person)p.clone(); System.out.println(clone); System.out.println(p.equals(clone)); System.out.println(p.getPet()==clone.getPet()); System.out.println("************"); clone.setAge(15); System.out.println(p); System.out.println(clone); System.out.println(p.equals(clone)); System.out.println("************"); clone.getPet().setName("小黄"); System.out.println(p); System.out.println(clone); System.out.println(p.equals(clone)); System.out.println(p.getPet()==clone.getPet()); }Cas de copie profondeAlors, comment implémenter la copie profonde ? La clé réside dans les lignes de code commentées dans le cas ci-dessus. La classe Pet remplace la méthode clone(). :
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!