Java, Save & open files with objectStream

Discussion in 'Programming' started by fex, Dec 20, 2010.

  1. #1
    Hello,

    I'm trying to save and open files by using the ObjectOutputStream and ObjectInputStream classes. I ensured that the object I'm writing is defined only by primitive types and implements Serializable.

    When saving objects:
    Layer 1
    Layer 2
    Layer 3
    Layer 4

    It will open:
    Layer 1
    Layer 3
    It skips always a full object, I'm obviously missing something...

    public static void saveImage() {
            ArrayList<Layer> layers = (ArrayList<Layer>) DrawingPanel.getInstance().getLayers();
            ObjectOutputStream outputStream = null;
            int option = fileChooser.showOpenDialog(Main.getInstance());
            if (option == JFileChooser.APPROVE_OPTION) {
                File file = fileChooser.getSelectedFile();
                try {
                    outputStream = new ObjectOutputStream(new FileOutputStream(file));
                    for (Layer layer : layers) {
                        outputStream.writeObject(layer);
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                } finally {
                    // close outputStream, left it out here
                }
            }
        }
    
        public static void openImage() {
            List<Layer> layers = new ArrayList<Layer>();
            ObjectInputStream inputStream = null;
            int option = fileChooser.showOpenDialog(Main.getInstance());
            if (option == JFileChooser.APPROVE_OPTION) {
                File file = fileChooser.getSelectedFile();
                try {
                    inputStream = new ObjectInputStream(new FileInputStream(file));
                    while (inputStream.readObject() != null) {
                        Layer layer = (Layer) inputStream.readObject();
                        layers.add(layer);
                    }
                } catch (EOFException e) {
                    e.printStackTrace();
                } finally {
                    // close inputStream, left it out here
                }
            }
            DrawingPanel.getInstance().setLayers(layers);
        }
    Code (markup):
    Tia
     
    fex, Dec 20, 2010 IP
  2. ThePHPMaster

    ThePHPMaster Well-Known Member

    Messages:
    737
    Likes Received:
    52
    Best Answers:
    33
    Trophy Points:
    150
    #2
    Can you post the entire java class?

    Two things I would check. First check if its actually writing all the layers after the save function.

    I will also step into the open function to check if it does read in all the layer objects.
     
    ThePHPMaster, Dec 21, 2010 IP
  3. MyEasyCpa

    MyEasyCpa Peon

    Messages:
    336
    Likes Received:
    1
    Best Answers:
    0
    Trophy Points:
    0
    #3
    Yeh can you post a bit more?
     
    MyEasyCpa, Dec 21, 2010 IP
  4. fex

    fex Peon

    Messages:
    89
    Likes Received:
    2
    Best Answers:
    0
    Trophy Points:
    0
    #4
    This put me to thinking in a new direction. The thing is that when invoking the readObject() method, the object is read and the ObjectInputStream moves along to the next object. So what happens is that by checking
    inputStream.readObject() != null
    Code (markup):
    you already passed/skipped an object ! Here's a simple solution using a boolean to check if the EOFException occured (the end of file is reached then):
        public static void openImage() {
            boolean isEnded = false;
            List<Layer> layers = new ArrayList<Layer>();
            ObjectInputStream inputStream = null;
            int option = fileChooser.showOpenDialog(Main.getInstance());
            if (option == JFileChooser.APPROVE_OPTION) {
                File file = fileChooser.getSelectedFile();
                try {
                    inputStream = new ObjectInputStream(new FileInputStream(file));
                    while (!isEnded) {
                        Layer layer = (Layer) inputStream.readObject();
                        layers.add(layer);
                    }
                } catch (EOFException e) {
                    isEnded = true;
                } catch (IOException e) {
                    e.printStackTrace();
                } catch (ClassNotFoundException e) {
                    e.printStackTrace();
                } finally {
                    try {
                        inputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
            DrawingPanel.getInstance().setLayers(layers);
        }
    Code (markup):
    Thanks!

    ps: Those two methods are all what takes to save & load objects into a file, that's all code to it...
     
    fex, Dec 22, 2010 IP
  5. fex

    fex Peon

    Messages:
    89
    Likes Received:
    2
    Best Answers:
    0
    Trophy Points:
    0
    #5
    Actually, to improve the code, try to handle downcasting better..

                try {
                    inputStream = new ObjectInputStream(new FileInputStream(file));
                    while (!isEnded) {
                        Object object = inputStream.readObject();
                        if (object instanceof Layer) {
                            Layer layer = (Layer) object;
                            layers.add(layer);
                        }
                    }
                }
    Code (markup):
     
    fex, Dec 22, 2010 IP
  6. haa

    haa Peon

    Messages:
    33
    Likes Received:
    0
    Best Answers:
    0
    Trophy Points:
    0
    #6
    The function inputStream.readObject(); is used as a condition in the while loop.
     
    haa, Dec 22, 2010 IP