Подтвердить что ты не робот

Что это значит: Сериализуемый класс не объявляет статическое окончательное поле serialVersionUID?

У меня есть предупреждающее сообщение, указанное в заголовке. Я хотел бы понять и удалить его. Я нашел несколько ответов на этот вопрос, но я не понимаю этих ответов из-за перегрузки с техническими терминами. Можно ли объяснить эту проблему простыми словами?

P.S. Я знаю, что такое ООП. Я знаю, что такое объект, класс, метод, поле и экземпляр.

P.P.S. Если кому-то нужен мой код, он находится здесь:

import java.awt.*;
import javax.swing.*;


public class HelloWorldSwing extends JFrame {

        JTextArea m_resultArea = new JTextArea(6, 30);

        //====================================================== constructor
        public HelloWorldSwing() {
            //... Set initial text, scrolling, and border.
            m_resultArea.setText("Enter more text to see scrollbars");
            JScrollPane scrollingArea = new JScrollPane(m_resultArea);
            scrollingArea.setBorder(BorderFactory.createEmptyBorder(10,5,10,5));

            // Get the content pane, set layout, add to center
            Container content = this.getContentPane();
            content.setLayout(new BorderLayout());
            content.add(scrollingArea, BorderLayout.CENTER);
            this.pack();
        }

        public static void createAndViewJFrame() {
            JFrame win = new HelloWorldSwing();
            win.setTitle("TextAreaDemo");
            win.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            win.setVisible(true);
        }

        //============================================================= main
        public static void main(String[] args) {
            SwingUtilities.invokeLater(new Runnable(){
                public void run(){
                    createAndViewJFrame();
                }
            });
        }

}
4b9b3361

Ответ 1

Из javadoc:

Сериализация сериализации связывает каждый сериализуемый класс с номером версии, называемым serialVersionUID, который используется во время десериализации для проверки того, что отправитель и получатель сериализованного объекта загружают классы для этого объекта, которые совместимы с сериализацией, Если получатель загрузил класс для объекта с другим serialVersionUID, чем у соответствующего класса отправителя, то десериализация приведет к InvalidClassException. Сериализуемый класс может объявить свой собственный serialVersionUID явно, объявив поле с именем "serialVersionUID", которое должно быть статическим, окончательным и длинным:

Вы можете настроить свою среду IDE на:

  • игнорировать это, вместо предупреждения.
  • автогенерировать id

В соответствии с вашим дополнительным вопросом: "Может ли быть, что обсуждаемое предупреждающее сообщение является причиной того, что мое приложение для графического интерфейса замерзает?":

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

Ответ 2

Причины для предупреждения описаны здесь, а простые исправления - отключить предупреждение или поместить в ваш код следующую декларацию для поставки UID версии. Фактическое значение не имеет значения, начинайте с 999, если хотите, но изменяя его, когда вы делаете несовместимые изменения в классе.

public class HelloWorldSwing extends JFrame {

        JTextArea m_resultArea = new JTextArea(6, 30);
        private static final long serialVersionUID = 1L;

Ответ 3

Другие ответы до сих пор содержат много технической информации. Я постараюсь ответить, как просили, простыми словами.

Сериализация - это то, что вы делаете с экземпляром объекта, если вы хотите сбросить его в необработанный буфер, сохранить его на диск, перенести в двоичный поток (например, отправить объект по сетевому сокету) или иначе создать сериализованное двоичное представление объекта. (Для получения дополнительной информации о сериализации см. Java Serialization в Википедии).

Если вы не собираетесь сериализовать свой класс, вы можете добавить аннотацию чуть выше своего класса @SuppressWarnings("serial").

Если вы собираетесь сериализовать, у вас есть множество вещей, чтобы беспокоиться о том, чтобы все было сосредоточено на правильном использовании UUID. В принципе, UUID - это способ "версии" объекта, который вы бы сериализовали, чтобы любой процесс де-сериализации знал, что он де-сериализуется правильно. Я бы посмотрел для обеспечения правильной проверки версий для сериализованных объектов.

Ответ 4

он должен изменяться всякий раз, когда что-либо изменения, влияющие на сериализацию (дополнительные поля, удаленные поля, изменение порядка поля,...)

Это не правильно, и вы не сможете назвать авторитетный источник этого иска. Он должен быть изменен всякий раз, когда вы вносите изменения, которые несовместимы с правилами, приведенными в разделе Versioning of Serializable Objects раздела Спецификация сериализации объектов, которая специально не включает дополнительные поля или изменение порядка полей, а также когда вы не указали readObject(), writeObject(), и/или readResolve() или /writeReplace() и/или объявление serializableFields, которое могло бы справиться с этим изменением.

Ответ 5

Любой класс, который может быть сериализован (т.е. реализует Serializable), должен объявить, что UID и он должен быть изменен всякий раз, когда какие-либо изменения влияют на сериализацию (дополнительные поля, удаленные поля, изменение порядка полей...). Значение поля проверяется во время десериализации, и если значение сериализованного объекта не равно значению класса в текущей виртуальной машине, генерируется исключение.

Обратите внимание, что это значение является особенным тем, что оно сериализуется с объектом, даже если оно является статическим по причинам, описанным выше.