2008-09-30 3 views
20

Мне интересно, можно ли смешать сериализацию объектов jdk 1.5 и 1.6 (Java 6) (бинарную связь). Я искал явное утверждение солнца по этому вопросу, но не получилось. Поэтому, помимо технической выполнимости, я ищу «официальное» заявление о проблеме.Является ли сериализация объекта Java совместимой между 1.5 и 1.6

+0

Я знаю, что это старый вопрос, но для будущих разработчиков, это то, что я использовал широко для продукта с клиентами, серверов, использующих POJO в течение нескольких лет. Сериализованные объекты между версиями работали без проблем. Единственный раз, когда у нас возникла проблема, - это когда мы нарушили правила сериализации. Например, не изменяйте тип переменной. – 2013-06-06 15:40:48

ответ

2

После тестирования с помощью сериализованного объекта, записанного в файл с использованием ObjectOutputStream в программе Java 1.5, затем выполните чтение с помощью ObjectInputStream в программе Java 1.6, я могу сказать, что это сработало без каких-либо проблем.

+0

Нет, вы не можете. Вы протестировали его на один класс. Одна ласточка не делает лето. – EJP 2017-01-01 09:04:53

16

Сам механизм сериализации не изменился. Для отдельных классов это будет зависеть от конкретного класса. Если класс имеет поле serialVersionUID, это должно указывать на совместимость с сериализацией.

Что-то вроде:

private static final long serialVersionUID = 8683452581122892189L; 

Если не изменится, то сериализованные версии совместимы. Для классов JDK это гарантировано, но, конечно, всегда можно забыть обновить serialVersionUID после внесения изменений.

Когда классы JDK не гарантируют совместимость, это обычно упоминается в Javadoc.

Внимание: Последовательные объекты этого класса не будут совместимы с будущими выпусками Swing-

2

я быстро добавить, что можно изменить класс, но забыть изменить serialVersionUID. Поэтому неверно: «Если класс определяет serialVersionUID, и это не изменяется, класс гарантированно совместим». Скорее, наличие того же serialVersionUID - это то, как API обещает обратную совместимость.

+0

Я предполагал, что вопрос о классах jdk и их идентификаторы serialVersionUID верны ... – Tom 2008-09-30 12:40:13

+0

Достаточно справедливо: если ваше обновление JDK испортит Serializable, клиенты вашего большого мальчика JDK (например, Sun, BEA, IBM и т. Д.)) должен кричать кровавое убийство (и у меня есть). По общему признанию, неясно, относится ли это только к классам JDK. – Alan 2008-10-01 02:15:33

2

Если не указано иное, это должно быть частью двоичной совместимости. Классы Swing явно не совместимы между версиями. Если вы обнаружили проблему с другими классами, сообщите об ошибке bugs.sun.com.

+0

Бинарная совместимость - это общедоступный и защищенный интерфейс, а совместимость с сериализацией - обычно с частными полями. Вы уверены, что кто-то подразумевает другого? – Tom 2008-09-30 12:38:42

2

Вы прочитали Java Object Serialization Specification? Есть тема на versioning. Существует также статья для исполнителей классов: Discover the secrets of the Java Serialization API. Каждый выпуск Java сопровождается compatibility notes.

С 6 спецификации Java на серийности:


Цели заключаются в следующем:

  • Поддержка двунаправленной связи между разными версиями одного класса, работающих в различных виртуальных машин с помощью:
    • Определение механизма, позволяющего классам JavaTM читать потоки, написанные более старыми версиями одного и того же класса.
    • Определение механизма, позволяющего классам JavaTM писать потоки, предназначенные для чтения более старыми версиями одного и того же класса.
  • Обеспечьте сериализацию по умолчанию для сохранения и для RMI.
  • Хорошо выполнять и создавать компактные потоки в простых случаях, чтобы RMI мог использовать сериализацию.
  • Уметь идентифицировать и загружать классы, соответствующие точному классу, используемому для записи потока.
  • Держите верхний минимум для неверсионных классов.
  • Используйте формат потока, который позволяет обходить поток без необходимости использовать методы, специфичные для объектов, сохраненных в потоке.

3

сериализации механизм в версии 1.5 и 1.6 совместим. Таким образом, тот же код, скомпилированный/работающий в контексте 1.5 и 1.6, может обмениваться сериализованными объектами. Являются ли два экземпляра VM одинаковой/совместимой версией класса (как может указывать поле serialVersionUID) - это другой вопрос, не связанный с версией JDK.

Если у вас есть один сериализуемый Foo.java и используйте его в 1.5 и 1.6 JDK/VM, сериализованные экземпляры Foo, созданные одним V; могут быть десериализованы другим.

0

Обратите внимание, что спецификация Java Beans описывает не зависящий от версии метод сериализации, который обеспечивает сильную обратную совместимость. Это также дает читаемые «сериализованные» формы. Фактически сериализованный объект можно легко создать с помощью механизма.

Посмотрите документацию на классы XMLEncoder и XMLDecoder.

Я бы не использовал это для передачи объекта по кабелю обязательно (хотя, если высокая производительность является требованием, я бы тоже не использовал сериализацию), но это неоценимо для постоянного хранения объектов.

0

Нельзя смешивать java 1.5 и 1.6. Например, у меня есть объекты Java 1.5, сериализованные в файл, и попытались открыть в java 1.6, но при этом возникла ошибка ниже

java.io.InvalidClassException: javax.swing.JComponent; локальный класс несовместимые: поток classdesc serialVersionUID = 7917968344860800289, локальный класс serialVersionUID = -1030230214076481435 в java.io.ObjectStreamClass.initNonProxy (Unknown Source) в java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) в java.io.ObjectInputStream. readClassDesc (Unknown Source) в java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) в java.io.ObjectInputStream.readClassDesc (Unknown Source) в java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) в java.io. ObjectInputStream.readClassDesc (Неизвестный источник) at java.io.ObjectInputStream.readOrdinaryObject (Неизвестный источник) at java.io.ObjectInputStream.readObject0 (Неизвестный источник) в java.io.ObjectInputStream.readArray (Unknown Source) в java.io.ObjectInputStream.readObject0 (Unknown Source) в java.io.ObjectInputStream.defaultReadFields (Unknown Source) в java.io.ObjectInputStream.readSerialData (Неизвестно Источник) на java.io.ObjectInputStream.readOrdinaryObject (Unknown Source) в java.io.ObjectInputStream.readObject0 (Unknown Source) в java.io.ObjectInputStream.defaultReadFields (Unknown Source) в java.io.ObjectInputStream.readSerialData (Неизвестный источник) at java.io.ObjectInputStream.readOrdinaryObject (Неизвестный источник) at java.io.ObjectInputStream.readObject0 (Неизвестный источник) at java.io.ObjectInputStream.readArray (Unknown Source) в java.io.ObjectInputStream.readObject0 (Unknown Source) в java.io.ObjectInputStream.defaultReadFields (Unknown Source) в java.io.ObjectInputStream.readSerialData (Unknown Source) в java.io. ObjectInputStream.readOrdinaryObject (Unknown Source) в java.io.ObjectInputStream.readObject0 (Unknown Source) в java.io.ObjectInputStream.readObject (Unknown Source)