Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What happens during serialization in java, if two object refrences are pointing to the same serializable Object?

What happens during serialization in java, if two object refrences are pointing to the same serializable Object? Does the Serializable Objects get saved twice ?
for example :

    class King implements java.io.Serializable {
        private String name="Akbar";
    }

    class Kingdom implements java.io.Serializable {
        King goodKing=new King();
        King badKing=goodKing;
    }

    public class TestSerialization {
        public static void serializeObject(String outputFileName,
                                           Object serializableObject) throws IOException {
            FileOutputStream fileStream=new FileOutputStream(outputFileName);
            ObjectOutputStream outStream=new ObjectOutputStream(fileStream);
            outStream.writeObject(serializableObject);
            outStream.close();
        }

        public static void main(String[] args) {
            Kingdom kingdom=new Kingdom();
            try {
                TestSerialization.serializeObject("Kingdom1.out", kingdom);
            }catch(IOException ex) {
                ex.getMessage();
            }
        }
    }

Now, whether only one object state is saved for both goodKing and badKing refrences or the King object get saved twice ?

like image 295
Amitesh Rai Avatar asked Jun 10 '14 08:06

Amitesh Rai


People also ask

What happens if the object to be serialized includes the references to other serializable objects?

Q6) What happens if the object to be serialized includes the references to other serializable objects? Ans) If the object to be serialized includes references to the other objects, then all those object's state also will be saved as the part of the serialized state of the object in question.

When you serialize an object what happens to the object references included in the object?

This is a recursive process. Thus when an object is serialized, all the included objects are also serialized alongwith the original obect. What one should take care of while serializing the object? One should make sure that all the included objects are also serializable.

What happens if an object is serializable but it includes a reference to a non serializable object?

If you try to serialize an object of a class which implements serializable, but the object includes a reference to an non-serializable class then a 'NotSerializableException' will be thrown at runtime.

What happens if the object to be serialized?

To serialize an object means to convert its state to a byte stream so way that the byte stream can be reverted back into a copy of the object. A Java object is serializable if its class or any of its superclasses implements either the java.


1 Answers

The documentation for ObjectOutputStream says what happens:

The default serialization mechanism for an object writes the class of the object, the class signature, and the values of all non-transient and non-static fields. References to other objects (except in transient or static fields) cause those objects to be written also. Multiple references to a single object are encoded using a reference sharing mechanism so that graphs of objects can be restored to the same shape as when the original was written.

(My emphasis)

E.g., if you have multiple references to a single object, when the graph is reconstituted, you end up with multiple references to a single reconstituted version of that object, not references to multiple equivalent instances of it.

Of course, if the container being serialized implements a different mechanism, the behavior is dictated by that mechanism, not the default one.

So for instance, if we have Thing and Test:

Thing.java:

import java.io.*;
import java.util.*;

public class Thing implements Serializable {
    private Map<String,String> map1;
    private Map<String,String> map2;

    public Thing() {
        this.map1 = new HashMap();
        this.map2 = this.map1; // Referring to same object
    }

    public void put(String key, String value) {
        this.map1.put(key, value);
    }

    public boolean mapsAreSameObject() {
        return this.map1 == this.map2;
    }
}

Test.java:

import java.io.*;

public class Test implements Serializable {

    public static final void main(String[] args) {
        try
        {
            // Create a Thing
            Thing t = new Thing();
            t.put("foo", "bar");

            // Write it out
            ObjectOutputStream os = new ObjectOutputStream(new FileOutputStream("foo"));
            os.writeObject(t);
            os.close();
            os = null;

            // Read it in
            Thing t2;
            ObjectInputStream is = new ObjectInputStream(new FileInputStream("foo"));
            t2 = (Thing)is.readObject();
            is.close();
            is = null;

            // Same underlying map for both properties?
            System.out.println("t2.mapsAreSameObject? " + t2.mapsAreSameObject());
        }
        catch (Exception e)
        {
            System.out.println("Exception: " + e.getMessage());
        }
    }
}

And run java Test, we get:

t2.mapsAreSameObject? true

...because both of Thing's members, map1 and map2 end up pointing to a single HashMap instance.

like image 110
T.J. Crowder Avatar answered Oct 02 '22 06:10

T.J. Crowder