Понимание клонирования объектов в Java с примерами
В этой статье мы обсуждаем интерфейс Cloneable, который указывает, что класс предоставил безопасный метод clone () . Чтобы понять, что означает клонирование, вспомните, что происходит, когда вы делаете копию переменной, содержащей ссылку на объект. Оригинал и копия являются ссылками на один и тот же объект. Это означает, что оригинал и копия взаимозависимы, т. Е. Изменение одного вызывает изменение и другого.
Если мы хотим, чтобы копия была новым объектом, который начинает свою жизнь идентичным оригиналу, но состояние которого может меняться со временем, мы должны использовать метод clone () .
Метод clone () объявлен защищенным в классе Object , поэтому наш код не может просто вызвать obj.clone () . Теперь мы можем спросить, но защищенные методы недоступны из любого подкласса, и не каждый класс является подклассом Object . К счастью, правила защищенного доступа гораздо более тонкие. Подкласс может вызывать метод protected clone () для клонирования собственных объектов. Мы должны переопределить клон, чтобы он был общедоступным, чтобы к нему можно было получить доступ любыми методами.
Несмотря на то, что реализация clone по умолчанию является адекватной, вам все равно необходимо реализовать интерфейс Clonable , переопределить метод clone (), чтобы он был общедоступным , и вызвать общедоступный .
Пример:
class Student implements Cloneable { // raise visibility level to public // and change the return type public Student clone() throws CloneNotSupportedException { return (Student) super .clone(); } . . . } |
Метод clone (), который вы только что видели, не добавляет функциональности к копии, предоставленной Object.clone . Он просто делает метод общедоступным и меняет его возвращаемый тип. Чтобы сделать более глубокую копию, мы должны клонировать изменяемые поля экземпляра.
This is the modified version:
class Student implements Cloneable { // other components public Student clone() throws CloneNotSupportedException { // call Object.clone() Student obj = (Student) super .clone(); // clone mutable fields obj.birthDay = (Date)birthDay.clone(); } } |
Метод clone () объекта будет пытаться вызвать исключение ClassNotSupportedException всякий раз, когда клон вызывается в классе, который не реализует интерфейс Cloneable.
Example:
import java.util.Date; import java.util.GregorianCalendar; public class Employee implements Cloneable { private String name; private double salary; private Date hireDay; public Employee(String name, double salary) { this .name = name; this .salary = salary; hireDay = new Date(); } public Employee clone() throws CloneNotSupportedException { // call Object.clone() Employee obj = (Employee) super .clone(); // clone mutable fields obj.hireDay = (Date)hireDay.clone(); return obj; } // Set the hireDay to a given date public void setHireDay( int year, int month, int day) { Date newHireDay = new GregorianCalendar(year, month - 1 , day) .getTime(); // instance field mutation hireDay.setTime(newHireDay.getTime()); } public void raiseSalary( double byPercent) { double raise = salary * byPercent / 100 ; salary += raise; } public String toString() { return ( "Employee[name=" + name + ", salary=" + salary + ", hireDay=" + hireDay + "]" ); } // main public static void main(String[] args) { try { Employee original = new Employee( "ABC X. YZ" , 50000 ); original.setHireDay( 2000 , 1 , 1 ); Employee copy = original.clone(); copy.raiseSalary( 10 ); copy.setHireDay( 2002 , 12 , 31 ); System.out.println( "original= " + original); System.out.println( "copy= " + copy); } catch (CloneNotSupportedException e) { e.printStackTrace(); } } } |
original= Employee[name=ABC X. YZ, salary=50000.0, hireDay=Sat Jan 01 00:00:00 UTC 2000]
copy= Employee[name=ABC X. YZ, salary=55000.0, hireDay=Tue Dec 31 00:00:00 UTC 2002]
Преимущества клонирования:
- В Java оператор '=' (присваивание) не может использоваться для клонирования, поскольку он просто создает копию ссылочных переменных. Чтобы преодолеть такое несоответствие, вместо оператора присваивания можно использовать метод clone () класса Object.
- Метод clone () - это защищенный метод класса Object, что означает, что только класс Employee может клонировать объекты Employee. Это означает, что ни один класс, кроме Employee, не может клонировать объекты Employee, поскольку он не знает атрибутов класса Employee.
Применение клонирования в Java :
- Он позволяет копировать объекты по полям, что удобно при работе с объектами схожих характеристик.
- Метод clone () по умолчанию можно исправить, вызвав clone для изменяемых подобъектов.
Вниманию читателя! Не переставай учиться сейчас. Ознакомьтесь со всеми важными концепциями Java Foundation и коллекций с помощью курса "Основы Java и Java Collections" по доступной для студентов цене и будьте готовы к работе в отрасли. Чтобы завершить подготовку от изучения языка к DS Algo и многому другому, см. Полный курс подготовки к собеседованию .