How to SerialVersionUID in java and related fast facts

View: 186    Dowload: 0   Comment: 0   Post by: hanhga  
Author: none   Category: Javascript   Fields: Other

0 point/0 review File has been tested

In java, serialization is the process of turning an object-in-memory into a stream of bytes so you can do stuff like store it on disk or send it over the network.

Introduction

In java, serialization is the process of turning an object-in-memory into a stream of bytes so you can do stuff like store it on disk or send it over the network. De-serialization is the reverse process: turning a stream of bytes into an object in memory. In my earlier post about “implementing serializable interface in java“, I shortly discussed the term serialVersionUID. In this post, I am expanding the discussion with more focus on this magical field.

As per java docs, during serialization, runtime associates with each serializable class a version number, called a serialVersionUID, which is used during de-serialization to verify that the sender and receiver of a serialized object have loaded classes for that object that are compatible with respect to serialization. If the receiver has loaded a class for the object that has a different serialVersionUID than that of the corresponding sender’s class, then de-serialization will result in an InvalidClassException. A serializable class can declare its own serialVersionUID explicitly by declaring a field named “serialVersionUID” that must be static, final, and of type long:

private static final long serialVersionUID = 4L;

Here, the serialVersionUID represents your class version, and you should increment it if the current version of your class is modified such that it is no longer backwards compatible with its previous version.

Serialization-deserialization-demo

Lets see an example of how a class is serialized and then de-serialized:

package com.howtodoinjava.demo.serialization;
 
import java.io.*;
import java.util.logging.Logger;
  
public class DemoClass implements java.io.Serializable {
  
    private static final long serialVersionUID = 4L;            //Default serial version uid
    private static final String fileName = "DemoClassBytes.ser"; //Any random name
    private static final Logger logger = Logger.getLogger("");
    //Few data fields
    //Able to serialize
    private static String staticVariable;
    private int intVariable;
     
    //Not able to serialize
    transient private String transientVariable = "this is a transient instance field";
    private Thread threadClass;
      
    public static void main(String[] args) throws IOException, ClassNotFoundException 
    {
        //Serialization
     
        DemoClass test = new DemoClass();
        test.intVariable = 1;
        staticVariable = "this is a static variable";
        writeOut(test);
        System.out.println("DemoClass to be saved: " + test);
     
        //De-serialization
         
        System.out.println("DemoClass deserialized: " + readIn());
    }
      
    private static Object readIn() throws IOException, ClassNotFoundException {
        ObjectInputStream ois = new ObjectInputStream(new FileInputStream(new File(fileName)));
        return ois.readObject();
    }
      
    private static void writeOut(java.io.Serializable obj) throws IOException {
        ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream(new File(fileName)));
        oos.writeObject(obj);
        oos.close();
    }
      
    @Override public String toString() {
        return "DemoClass: final static fileName=" + fileName + ", final static logger=" + logger
                + ", non-final static staticVariable=" + staticVariable + ", instance intVariable=" + intVariable
                + ", transient instance transientVariable=" + transientVariable + ", non-serializable instance field threadClass:=" + threadClass;
    }
}
 
Ouput:
 
DemoClass to be saved: DemoClass: 
final static fileName=DemoClassBytes.ser, 
final static logger=java.util.logging.LogManager$RootLogger@1d99a4d, 
non-final static staticVariable=this is a static variable, 
instance intVariable=1, 
transient instance transientVariable=this is a transient instance field, 
non-serializable instance field threadClass:=null
 
//Execute readIn() function from a separate main() method 
//to get given below output correctly. It will flush out the static fields.
 
DemoClass deserialized: DemoClass: 
final static fileName=DemoClassBytes.ser, 
final static logger=java.util.logging.LogManager$RootLogger@cd2c3c, 
non-final static staticVariable=null, 
instance intVariable=1, 
transient instance transientVariable=null, 
non-serializable instance field threadClass:=null

If a serializable class does not explicitly declare a serialVersionUID, then the serialization runtime will calculate a default serialVersionUID value for that class based on various aspects of the class.

However, it is strongly recommended that all serializable classes explicitly declare serialVersionUID values, since the default serialVersionUID computation is highly sensitive to class details that may vary depending on compiler implementations and can produce different serialVersionUID in different environments. This can result in unexpected InvalidClassException during de-serialization.

Therefore, to guarantee a consistent serialVersionUID value across different java compiler implementations, a serializable class must declare an explicit serialVersionUID value. It is also strongly advised that explicit serialVersionUID declarations use the private modifier in serialVersionUID where possible, since such declarations apply only to the immediately declaring class. SerialVersionUID field is not useful as inherited member.

Based on my short career, I can say that storing serialized data for such a long time span [Spatial serialization] is not very common. It is far more common to use the serialization mechanism to temporarily write data [Temporal serialization] to for instance a cache or send it over the network to another program to utilize the information. In this case you are not interested in maintaining backwards compatibility. You are only concerned with making sure that the code bases which are communicating on network, indeed have the same version of relevant classes. In order to facilitate such a check, you must maintain the serialVersionUID just as it and don’t change it. Also, do not forget to update it when making incompatible changes to your classes, on both side applications on network.

Dealing with classes without serialVersionUID

It is not the situation which we ever want to face. But, it’s reality and sometimes it happen (should i say rarely?). If you need to change such class in incompatible way but wan to maintain serialization/deserialization capability w/ old version of the class, you can use the JDK tool “serialver” to generate the serialVersionUID on the old class, and explicitly set that on the new class. Do not forget to to implement readObject() and writeObject() methods because the built-in de-serialization mechanism (in.defaultReadObject()) will refuse to de-serialize from old versions of the data.

If you define your own readObject() function which can read back old data. This custom code should check the serialVersionUID in order to know which version the data is in and decide how to de-serialize it. This versioning technique is useful if you store serialized data which survives several versions of your code.

I believe that if you are working on a project which will be deployed in distributed environment then it is required to have the UID, since different compilers may (mostly) produce different ids, and you don’t know what compiler your client bytecode will be built with in some instances

Fast facts:

  1. Transient and static fields are ignored in serialization. After de-serialization transient fields and non-final static fields will be null. Final static fields still have values since they are part of the class data.
  2. ObjectOutputStream.writeObject(obj) and ObjectInputStream.readObject() are used in serialization and de-serialization.
  3. During serialization, you need to handle IOException; during de-serialization, you need to handle IOException and ClassNotFoundException. So the de-serializaed class type must be in the classpath.
  4. Uninitialized non-serializable, non-transient instance fields are tolerated. When adding “private Thread th;”, no error in serializable. However, “private Thread threadClass = new Thread();” will cause exception:
Exception in thread "main" java.io.NotSerializableException: java.lang.Thread
at java.io.ObjectOutputStream.writeObject0(Unknown Source)
at java.io.ObjectOutputStream.defaultWriteFields(Unknown Source)
at java.io.ObjectOutputStream.writeSerialData(Unknown Source)
at java.io.ObjectOutputStream.writeOrdinaryObject(Unknown Source)
at java.io.ObjectOutputStream.writeObject0(Unknown Source)
at java.io.ObjectOutputStream.writeObject(Unknown Source)
at com.howtodoinjava.demo.serialization.DemoClass.writeOut(DemoClass.java:42)
at com.howtodoinjava.demo.serialization.DemoClass.main(DemoClass.java:27)
  1. Serialization and de-serialization can be used for copying and cloning objects. It is slower than regular clone, but can produce a deep copy very easily.
  2. If I need to serialize a Serializable class Employee, but one of its super classes is not Serializable, can Employee class still be serialized and de-serialized? The answer is yes, provided that the non-serializable super-class has a no-arg constructor, which is invoked at de-serialization to initialize that super-class.
  3. You must be careful while modifying a class implementing java.io.Serializable. If class does not contain a serialVersionUID field, its serialVersionUID will be automatically generated by the compiler. Different compilers, or different versions of the same compiler, will generate potentially different values.
  4. Computation of serialVersionUID is based on not only fields, but also on other aspect of the class like implement clause, constructors, etc. So the best practice is to explicitly declare a serialVersionUID field to maintain backward compatibility. If you need to modify the serializable class substantially and expect it to be incompatible with previous versions, then you need to increment serialVersionUID to avoid mixing different versions.

How to SerialVersionUID in java and related fast facts

How to SerialVersionUID in java and related fast facts Posted on 27-07-2016  In java, serialization is the process of turning an object-in-memory into a stream of bytes so you can do stuff like store it on disk or send it over the network. 5/10 186

Comment:

To comment you must be logged in members.

Files with category

  • JUnit 5 State Of The Union using java

    View: 602    Download: 0   Comment: 0   Author: none  

    JUnit 5 State Of The Union using java

    Category: Javascript
    Fields: Other

    2.25/2 review
    JUnit 5 has been under development for about 14 months now and the prototype is almost a year old. Time to summarize what happened so far, where the project stands, and where it’s going.

  • Getting Started with Dropwizard using java

    View: 691    Download: 0   Comment: 0   Author: none  

    Getting Started with Dropwizard using java

    Category: Javascript
    Fields: Other

    2.25/2 review
    Dropwizard is a framework for building RESTful web services in Java. In this tutorial we’re going to have a look at how to get started with developing a Dropwizard application by building a new service from scratch.

  • Build Query NULL Value in MySql

    View: 319    Download: 0   Comment: 0   Author: none  

    Build Query NULL Value in MySql

    Category: Javascript
    Fields: Other

    2.5/2 review
    Misunderstanding NULL is common mistake beginners do while writing MySql query. While quering in MySql they compare column name with NULL. In MySql NULL is nothing or in simple word it isUnknown Value so if you use comparison operator for NULL values...

  • Manage Your JavaScript Application State with MobX

    View: 336    Download: 0   Comment: 0   Author: none  

    Manage Your JavaScript Application State with MobX

    Category: Javascript
    Fields: Other

    2.25/2 review
    This article was peer reviewed by Michel Weststrate and Aaron Boyer. Thanks to all of SitePoint’s peer reviewers for making SitePoint content the best it can be!

  • Build Bringing Pages to Life with the Web Animations API

    View: 346    Download: 0   Comment: 0   Author: none  

    Build Bringing Pages to Life with the Web Animations API

    Category: Javascript
    Fields: Other

    4.5/2 review
    This article is by guest author Dudley Storey. SitePoint guest posts aim to bring you engaging content from prominent writers and speakers of the JavaScript community.

  • How to Style Google Custom Search Manually

    View: 325    Download: 0   Comment: 0   Author: none  

    How to Style Google Custom Search Manually

    Category: Javascript
    Fields: Other

    0/0 review
    Website owners very often decide on using Google’s Custom Search Engine (GCSE) for searching through their content instead of using built-in and/or custom search functionality. The reason is simple – it’s much less work, and most often it does the...

  • Test React Components Using Jest

    View: 5098    Download: 0   Comment: 0   Author: none  

    Test React Components Using Jest

    Category: Javascript
    Fields: Other

    4.5/1 review
    This article is by guest author Jack Franklin. SitePoint guest posts aim to bring you engaging content from prominent writers and speakers of the JavaScript community.

  • Programming Question Reverse String without using String function

    View: 783    Download: 0   Comment: 0   Author: none  

    Programming Question Reverse String without using String function

    Category: Javascript
    Fields: Other

    4.5/1 review
    Write a program to reverse string without using string function. You don’t have to use any in-built string library function. This problem can be solved by multiple approaches. Let’s check it.

 

File suggestion for you

File top downloads

logo codetitle
Codetitle.com - library source code to share, download the file to the community
Copyright © 2015. All rights reserved. codetitle.com Develope by Vinagon .Ltd