Tuesday, September 11, 2012

Short explain of Externalization


Externalization is nothing but serialization but by implementing Externalizable interface to persist and restore the object. To externalize your object, you need to implement Externalizable interface that extends Serializable interface. Here only the identity of the class is written in the serialization stream and it is the responsibility of the class to save and restore the contents of its instances which means you will have complete control of what to serialize and what not to serialize. But with serialization the identity of all the classes, its superclasses, instance variables and then the contents for these items is written to the serialization stream. But to externalize an object, you need a default public constructor.
Unlike Serializable interface, Externalizable interface is not a marker interface and it provides two methods - writeExternal and readExternal. These methods are implemented by the class to give the class a complete control over the format and contents of the stream for an object and its supertypes. These methods must explicitly coordinate with the supertype to save its state. These methods supersede customized implementations of writeObject and readObject methods.
How serialization happens? JVM first checks for the Externalizable interface and if object supports Externalizable interface, then serializes the object using writeExternal method. If the object does not support Externalizable but implement Serializable, then the object is saved using ObjectOutputStream. Now when an Externalizable object is reconstructed, an instance is created first using the public no-arg constructor, then the readExternal method is called. Again if the object does not support Externalizable, then Serializable objects are restored by reading them from an ObjectInputStream.
 
/**
 * Externalizable Impl
 */
package com;

import java.io.Externalizable;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectInputStream;
import java.io.ObjectOutput;
import java.io.ObjectOutputStream;

/**
 * @author thanooj
 *
 */
public class Employee implements Externalizable {

    private int empId;
    private String firstName;
    private String lastName;
    private int age;
   
    public Employee() {}
   
    public Employee(int empId, String firstName, String lastName, int age) {
        super();
        this.empId = empId;
        this.firstName = firstName;
        this.lastName = lastName;
        this.age = age;
    }

    /* (non-Javadoc)
     * @see java.io.Externalizable#readExternal(java.io.ObjectInput)
     * Note: we need to follow the order of writeExternal did.
     */
    @Override
    public void readExternal(ObjectInput in) throws IOException,
            ClassNotFoundException {
        empId = in.readInt();
        firstName = (String)in.readObject();
        age = in.readInt();
    }

    /* (non-Javadoc)
     * @see java.io.Externalizable#writeExternal(java.io.ObjectOutput)
     */
    @Override
    public void writeExternal(ObjectOutput out) throws IOException {
        out.writeInt(empId);
        out.writeObject(firstName);
        out.writeInt(age);
    }

    @Override
    public String toString() {
        return empId + " "+firstName+" "+lastName+" "+age;
    }
   
    public static void main(String[] args) {
        Employee empSe = new Employee(1, "rama", "sri", 29);
        Employee empDe = null;
        //serialize the car
        try {
            FileOutputStream fo = new FileOutputStream("tmp");
            ObjectOutputStream so = new ObjectOutputStream(fo);
            so.writeObject(empSe);
            so.flush();
        } catch (Exception e) {
            e.printStackTrace();
        }

        // de-serialize the Car
        try {
            FileInputStream fi = new FileInputStream("tmp");
            ObjectInputStream si = new ObjectInputStream(fi);         
            empDe = (Employee) si.readObject();
            System.out.println(empDe);
        }
        catch (Exception e) {
             e.printStackTrace();
        }
    }
}

output:
--------
1 rama null 29

No comments: