Serialization: Serialization is a mechanism of converting the state of an object into a byte stream.
Deserialization: Deserialization is a mechanism to convert back to object from the byte stream.
Why?
This serialization and deserialization helps us in many scenarios like gaming, session state management etc.
Let’s understand this by examining computer games.
When we stop or pause a running computer game, it usually starts from the state where it was left off when we play it again. This is possible through the process of Serialization; which is saving the current object state as byte stream into file or database. Then to restore the object’s state when we access the game again is called Deserialization.
We will understand term defined in serialization process.

What is stream?
A stream is nothing but the sequence of data elements. In a computer system, there is a source that generates data in the form of stream and there is a destination which reads and consumes this stream. Here are the types of streams:
- Byte Stream: Byte stream does not have any encoding scheme and it uses 8-bit (or one byte) to store a single character. Byte stream is a low level input output (I/O) operation that can be performed by a JAVA program. To process such byte stream, we need to use a buffered approach for IO operations.
- Character Stream: Character stream is composed of the streams of characters with proper encoding scheme such as ASCII, UNICODE, or any other format. Unlike byte stream, the character stream will automatically translate to and from the local character set. JAVA language uses UNICODE system to store characters as character stream.
- Data Stream: Data Stream is used to perform binary IO operations for all the primitive data types in Java. We can perform I/O operations in an efficient and convenient way for Boolean, char, byte, short, int, long, float, double, and Strings, etc. by using data stream. It also allows us to read-write Java primitive data types instead of raw bytes.
- Object Stream: the state of a JAVA object can be converted into a byte stream that can be stored into a database, file, or transported to any known location like from web tier to app tier as data value object in client-server RMI applications. This process of writing the object state into a byte stream is known as Serialization.
When we will use serialization and deserialization?
In multi-tier JAVA/J2EE application (client-server RMI applications), when we make a remote invocation method or RMI from a web tier to app tier, we need to send the
Marker Interface
An interface in Java without any field and method is a Marker interface. It is used to inform compiler that the class implementing it has some special behavior or meaning. Some of the Marker interfaces are-
java.io.Serializable java.rmi.Remote java.util.RandomAccess java.lang.Cloneable
Although since Java 5 marker interfaces are replaced by annotations and they serve the same purpose as marker interfaces did before but for serializability we still use the interfaces and the
Data and Object Stream Interfaces
The following are the data and object stream interfaces which every Object Stream class implements. Object Stream class implements either of the two interfaces.
ObjectInput : It is the sub interface ofDataInput ObjectOutput : It is the sub interface ofDataOutput
Note: All the primitive data I/O methods which are already covered in Data Streams are also implemented in object streams because these interfaces are the sub interface of Data streams interfaces.
Object Streams Classes
The following are the two classes used for Object Streams.
-
ObjectInputStream
- This Java class is responsible for the deserialization of the serialized objects and the primitive data.
- This class helps to read the object from the graph of objects stored while using
FileInputStream . - It has a main method
readObject() that is used to deserialize the object. It reads the class of the object, the signature of the class, and the values of the non-transient and non-static fields of the class, and all of its super types. Here is the method.012public final Object readObject() throws IOException, ClassNotFoundException
-
ObjectOutputStream
- This class is responsible for the serialization of an object. It stores data primitives and a graph of Java object that are available to ObjectInputStream to read data from.
- It has a main
writeObject() method that saves the super class and sub class data of a class or in other words, it serializes the object directly.012public final void writeObject(Object object) throws IOException
Transient Keyword
There are scenarios in which we want to store only a part of the object i.e. we want to omit some specific fields from the stored object just like password field from any user class or an Employee or you can think of any other sensitive information.
In these cases we mark these fields as
0 1 2 |
transient private String password; |
Serialization and Deserialization Example
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 |
package com.codenuclear.serialization; import java.io.Serializable; public class UserVO implements Serializable { private static final long serialVersionUID = -8744169653811326042L; private String name; private String username; private transient String password; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } @Override public String toString() { return "User [name=" + name + ", username=" + username + ", password=" + password + "]"; } } |
- Make sure that the Java class you need to store must implement
Serializable interface. - Notice that password field in the above class is made transient because it is a sensitive information and we don’t want to store it or you can chose any other field.
- Also there is another field named
serialVersionUID which is a Long variable and it should be defined for all the Java classes because if it is not and if in future we need to perform any changes in the class like variables, methods etc then we would never be able to deserialize an already serialized object.
You can try it yourself by first serializing the object and then do some changes in your java class before deserializing it. You will get an error stating the change in SerialVersionUID which is generated automatically by the compiler.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
package com.codenuclear.serialization; import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; public class Serializer { /** * deserialize to Object from given file. We use the general Object so as that it can work for any Java Class. */ public static Object deserialize(String fileName) throws IOException, ClassNotFoundException { FileInputStream fis = new FileInputStream(fileName); BufferedInputStream bis = new BufferedInputStream(fis); ObjectInputStream ois = new ObjectInputStream(bis); Object obj = ois.readObject(); ois.close(); return obj; } /** * serialize the given object and save it to given file */ public static void serialize(Object obj, String fileName) throws IOException { FileOutputStream fos = new FileOutputStream(fileName); BufferedOutputStream bos = new BufferedOutputStream(fos); ObjectOutputStream oos = new ObjectOutputStream(bos); oos.writeObject(obj); oos.close(); } } |
- This class has two methods, first for deserialization, and the other is for serialization.
- The
serialize method accepts the file path and name which has the byte stream of an object’s state and returns the Object that can be down casted to the corresponding serialized class object. - In this
deserialize method; first we open the file in read mode usingFileInputStream class then we pass the object of this file toBufferedInputStream class constructor while instantiating it, which speeds up the reading operation. The object ofBufferedInputStream class is passed to the constructor of classObjectInputStream while instantiating this class. We can call thereadObject() method of this class which will carry out the actual deserialization. - Lastly, close the
ObjectInputStream object and return the deserialized data value object. - The
serialize method accepts two parameters; i.e. the file path & name, and the data value object that is required to be serialized. - In this
serialize method first we open the file in write mode usingFileOutputStream class then we pass the object of this file toBufferedOutputStream class constructor while instantiating it, which speeds up the writing operation. The object ofBufferedOutputStream class is passed to the constructor of classObjectOutputStream while instantiating this class. We can call thewriteObject(object) method of this class to serialize the data value object and write the byte stream into the opened file. - Lastly close the
ObjectOutputStream object.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
package com.codenuclear.serialization; import java.io.IOException; public class SerializationTest { public static void main(String[] args) { UserVO user = new UserVO(); user.setName("CodeNuclear"); user.setUsername("codenuclear"); user.setPassword("codenuclear"); try { /** * Serializing the object */ Serializer.serialize(user, "serialization.txt"); /** * Deserializing the object */ UserVO newUser = (UserVO) Serializer.deserialize("serialization.txt"); System.out.println(newUser.toString()); } catch (IOException | ClassNotFoundException e) { e.printStackTrace(); } } } |
Output:
Your web has proven useful to me.