Write to disk an object that contains a BufferedImage

2.6k views Asked by At

I have an object BatchState that has pointers to a number of pieces of data, including a BufferedImage. I need to serialize the object.

Here's a simplified version of my BufferedImage:

public class BatchState implements Serializable{
    private int anInt;
    //A bunch of other primitives and objects
    //...
    private transient Image image; //This is the BufferedImage

    //Constructors, methods, and so forth
    //...
}

I have made the Image transient so that I can then write it to a different file using ImageIO.

I am trying to serialize the object using this code:

public void saveState(){
    ObjectOutputStream oos = null;
    FileOutputStream fout = null;
    try{
        fout = new FileOutputStream("data/saved/"+Client.getUser()+".sav", true);
        oos = new ObjectOutputStream(fout);
        oos.writeObject(batchState);
        oos.close();
    } catch (Exception e) {
        e.printStackTrace();
    } 
}

However, any time I call this method, my program throws the follow exception:

java.io.NotSerializableException: java.awt.image.BufferedImage

This in spite of the fact that the BufferedImage is transient.

I am looking for one of two solutions:

  1. Find a way to serialize the BufferedImage along with the rest of the data, or
  2. Find a way to serialize the BatchState to one file and then write the BufferedImage to a separate file.

Either solution is fine.

2

There are 2 answers

1
Benjamin On BEST ANSWER

Solved. It involved some other data that I didn't include in the code that I showed above. Your guys' comments helped me realize what the problem was, though.

It turns out that the BufferedImage there visible wasn't the problem at all. I had a pointer to another object which ALSO contained a BufferedImage, and it was that other BufferedImage (nested in another object) that was causing the OutputStream to throw its exception.

Moral of the story: ObjectOutputStream will serialize even deeply nested objects.

0
user207421 On

You could write yourself a custom writeObject() method that calls first out.defaultWriteObject() and then ImageIO.write(image, "jpeg", out) (or whatever format you prefer, and similarly a custom readObject() method that does the converse. See the Object Serialization Specification for the correct signatures of these methods.