Serialization lets you save an object’s state. Deserialiszation is a process of retrieving saved object state. By using serialization technique you can save an object on a file, send it over network and then use the same object state.
Serializable
It is a marker interface which should be implemented by class which you want to make serializable. It is used as a label. This interface does not specify any methods or constants. In fact, In Serializable.java file you will see only following code.
public interface Serializable {}
well, except package statement.
serialVersionUID
Java serialization uses a version number for each class, which is defined by field named serialVersionUID. It is used while deserializing an object. If serialVersionUID of class of serialized object is different from class which is used to deserialize the object then java throws InvalidClassException. It looks like this.
Exception in thread "main" java.io.InvalidClassException: in.blogspot.abjava.concept.Student; local class incompatible: stream classdesc serialVersionUID = 1, local class serialVersionUID = 2
You will be able to get this exception from below example. Just, comment deserialization part of code and run it once. Then uncomment deserialization, comment serialization part and change serialVersionUID to 2L. Again run the program.
You will be able to get this exception from below example. Just, comment deserialization part of code and run It once. Then uncomment deserialization, comment serialization part and change serialVersionUID to 2L. Again run the program.
If a serializable class does not declare a serialVersionUID then serialization runtime calculate it on the basis of various aspects.You can read more about them here. But It is recommended that You explicitly specify serialVersionUID in your serializable class. Because serialVersionUID computation is based on features that is depending on compiler implementation. So, you may get wrong InvalidClassException and deserialization will fail.
A serialVersionUID can be defined in following way :
ANY-ACCESS-MODIFIER static final long serialVersionUID = 42L;
Further, It is good practice to use private modifier for serialVersionUID as inherited members will not have any use of this field.
Transient Keyword
If any field of a class is declared with transient keyword. Then such field will be skipped while serializing. Like in the example. I have skipped course variable.
Example Program
Following example shows use of Serializable interface and Object I/O streams.
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
/**
* Created by dinsaw on 12/13/2014.
* for all example source code visit : https://github.com/dinsaw/abjava
*/
public class SerializableDemo {
public static final String FILE_NAME = "stud.data";
public static void main(String... args) throws IOException, ClassNotFoundException {
Student student = new Student("Din",1,"CS");
System.out.println("student = " + student);
//Serializing object
FileOutputStream fos = new FileOutputStream(FILE_NAME);
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(student);
System.out.println("Object saved.");
//De serializing object
FileInputStream fis = new FileInputStream(FILE_NAME);
ObjectInputStream ois = new ObjectInputStream(fis);
Student student1 = (Student) ois.readObject();
System.out.println("Object read completed.");
System.out.println("student1 = " + student1);
}
}
/**
* A POJO class which implements Serializable interface.
*/
class Student implements Serializable {
/**
* serialVersionUID defines class version. Whenever you will modify the class Student
* it is better to change serialVersionUID.
*/
private static final long serialVersionUID = 1L;
private String name;
private int rollNum;
/**
* course will not be serialized.
*/
private transient String course;
Student(String name, int rollNum, String course) {
this.name = name;
this.rollNum = rollNum;
this.course = course;
}
public int getRollNum() {
return rollNum;
}
public void setRollNum(int rollNum) {
this.rollNum = rollNum;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", rollNum=" + rollNum +
", course='" + course + '\'' +
'}';
}
}
After executing above java program you will be able to see file named stud.data in your project root directory or program directory. It looks like this.
��sr"in.blogspot.abjava.concept.Student5@چg�IrollNumLnametLjava/lang/String;xptDin
Output
student = Student{name='Din', rollNum=1, course='CS'}
Object saved.
Object read completed.
student1 = Student{name='Din', rollNum=1, course='null'}