Главная страница

Ответы на вопросы по ревью 4. Java io. Ключевым понятием здесь является понятие потока


Скачать 1.93 Mb.
НазваниеJava io. Ключевым понятием здесь является понятие потока
Дата03.07.2022
Размер1.93 Mb.
Формат файлаdoc
Имя файлаОтветы на вопросы по ревью 4.doc
ТипДокументы
#623608
страница27 из 39
1   ...   23   24   25   26   27   28   29   30   ...   39

Особенности сериализации Date


Если объект сериализации включает поля типа Date, то здесь следует, при необходимости, учитывать временной сдвиг между различными регионами. В противном случае может возникнуть ситуация, при которой на сервере будет создан объект Date с одним временем в определенной TimeZone, а на клиенте он будет десериализован с другой TimeZone. В зависимости от времени создания игнорирование TimeZone может привести к изменению даты. Решение данной проблемы представлено на странице описания TimeZone.

Использование сериализации


Технология RMI (Java Remote Method Invocation), построенная на сериализации, позволяет java-приложению, запущенному на одной виртуальной машине, вызвать методы объекта, работающего на другой виртуальной машине JVM (Java Virtual Machine).

12) Клонирование объекта. Глубокое и поверхностное.

Для клонирования объекта в Java можно пользоваться тремя способами:



  1. Переопределение метода clone() и реализация интерфейса Cloneable();

  2. Использование конструктора копирования;

  3. Использовать для клонирования механизм сериализации


Теперь по порядку. Первый способ подразумевает, что вы будете использовать механизм так называемого «поверхностного клонирования» и сами позаботитесь о клонировании полей-объектов. Метод clone() в родительском классе Object является protected, поэтому требуется переопределение его с объявлением как public. Он возвращает экземпляр объекта с копированными полями-примитивами и ссылками. И получается что у оригинала и его клона поля-ссылки указывают на одни и те же объекты. Пример далее показывает, как одновременно меняется поле у оригинального объекта и клона.
public class CloneTest{

static class Person implements Cloneable{

String name;

int age;

Car car;

Person(Car car,int age,String name) {

this.car = car;

this.age = age;

this.name = name;

}
@Override

public String toString() {

return this.name+" {" +

"age=" + age +

", car=" + car +

'}';

}
@Override

protected Object clone() throws CloneNotSupportedException {

return super.clone();

}

}

static class Car{

public String color;
Car(String color) {

this.color = color;

}
@Override

public String toString() {

return "{" +

"color car='" + color + '\'' +

'}';

}

}

public static void main(String[] args) throws CloneNotSupportedException {

Car car = new Car("Green");

Person person=new Person(car,25,"Mike");
Person clone = (Person) person.clone();

System.out.println(person);

System.out.println(clone);

clone.name=new String("Ivan");

clone.car.color="red";

System.out.println(person);

System.out.println(clone);

}

}

Вывод:

Mike {age=25, car={color car='Green'}}

Mike {age=25, car={color car='Green'}}

Mike {age=25, car={color car='red'}}

Ivan {age=25, car={color car='red'}}


Из примера выше видно, что у клона и оригинала состояние одного из полей изменяется одновременно. Следующий способ заключается в использовании конструктора копирования:
public class Person {

private int age;

private String name;

public Person(int age, String name){

this.age=age;

this.name=name;

}

// конструктор копии

public Person(Person other) {

this(other.getAge(), other.getName());

}
public int getAge() {

return age;

}
public void setAge(int age) {

this.age = age;

}
public String getName() {

return name;

}
public void setName(String name) {

this.name = name;

}
@Override

public String toString() {

return "Person{" +

"age=" + age +

", name='" + name + '\'' +

'}';

}
public static void main(String[] args) {

Person original = new Person(18, "Grishka");

Person clone = new Person(original);

System.out.println(original);

System.out.println(clone);

}

}

Вывод:

Person{age=18, name='Grishka'}

Person{age=18, name='Grishka'}


В классе описывается конструктор, который принимает объект этого же класса и инициализирует значениями его полей поля нового объекта. О реализации инициализации полей полностью должен позаботиться разработчик класса.

Но оба вышеуказанных способа полны потенциальных ошибок и по сути создают копию объекта. Наиболее удобным и гибким способом клонирования является механизм сериализации. Он заключается в сохранении объекта в поток байтов с последующей эксгумацией его от туда. Для примера пригласим кота Ваську, его ждёт пара опытов:
import java.io.*;
class Cat implements Serializable{

private String name;

private String color;

private int age;
public Cat(String name, String color, int age) {

this.name = name;

this.color = color;

this.age = age;

}
public String getColor() {

return color;

}
public void setColor(String color) {

this.color = color;

}
@Override

public String toString() {

return "Cat{" +

"name='" + name + '\'' +

", color='" + color + '\'' +

", age=" + age +

'}';

}

}

public class BasketCats{

public static void main(String[] args) throws IOException, ClassNotFoundException {

Cat vaska = new Cat("Vaska","Gray",4);

ByteArrayOutputStream baos = new ByteArrayOutputStream();

ObjectOutputStream ous = new ObjectOutputStream(baos);

//сохраняем состояние кота Васьки в поток и закрываем его(поток)

ous.writeObject(vaska);

ous.close();

ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray());

ObjectInputStream ois = new ObjectInputStream(bais);

//создаём кота для опытов и инициализируем его состояние Васькиным

Cat cloneVaska = (Cat)ois.readObject();

System.out.println(vaska);

System.out.println(cloneVaska);

System.out.println("*********************************************");

cloneVaska.setColor("Black");

//Убеждаемся что у кота Васьки теперь есть клон, над которым можно ставить опыты без ущерба Василию

System.out.println(vaska);

System.out.println(cloneVaska);
}

}

Вывод:

Cat{name='Vaska', color='Gray', age=4}

Cat{name='Vaska', color='Gray', age=4}

*********************************************

Cat{name='Vaska', color='Gray', age=4}

Cat{name='Vaska', color='Black', age=4}


Ни один кот не пострадал в результате тестов, мы видим что Васька был сохранён в поток, из которого затем восстановили независимый клон. Если нет особой необходимости обработки полей во время клонирования объектов, то сериализация является наиболее предпочтительным вариантом для этих целей.

1   ...   23   24   25   26   27   28   29   30   ...   39


написать администратору сайта