I'm writing a little Java program (it's an ImageJ plugin, but the problem is not specifically ImageJ related) and I have some problem, most probably due to the fact that I never really programmed in Java before...
So, I have a Vector of Vectors and I'm trying to save it to a file and read it.
The variable is defined as:
Vector <Vector <myROI> > ROIs = new Vector <Vector <myROI> >();
where myROI
is a class that I previously defined.
Now, to write the vector to a file I use:
void saveROIs()
{
SaveDialog save = new SaveDialog("Save ROIs...", imp.getTitle(), ".xroi");
String name = save.getFileName();
if (name == null)
return;
String dir = save.getDirectory();
try
{
FileOutputStream fos = new FileOutputStream(dir+name);
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(ROIs);
oos.close();
}
catch (Exception e)
{
IJ.log(e.toString());
}
}
This correctly generates a binary file containing (I suppose) the object ROIs
.
Now, I use a very similar code to read the file:
void loadROIs()
{
OpenDialog open = new OpenDialog("Load ROIs...", imp.getTitle(), ".xroi");
String name = open.getFileName();
if (name == null)
return;
String dir = open.getDirectory();
try
{
FileInputStream fin = new FileInputStream(dir+name);
开发者_C百科 ObjectInputStream ois = new ObjectInputStream(fin);
ROIs = (Vector <Vector <myROI> >) ois.readObject(); // This gives error
ois.close();
}
catch (Exception e)
{
IJ.log(e.toString());
}
}
But this function does not work.
First, I get a warning:
warning: [unchecked] unchecked cast found : java.lang.Object
required: java.util.Vector<java.util.Vector<myROI>>
ROIs = (Vector <Vector <myROI> >) ois.readObject();
^
I Googled for that and see that I can suppress by prepending @SuppressWarnings("unchecked")
, but this just makes things worst, as I get an error:
<identifier> expected
ROIs = (Vector <Vector <myROI> >) ois.readObject();
^
In any case, if I omit @SuppressWarnings
and ignore the warning, the object is not read and an exception is thrown
java.io.WriteAbortedException: writing aborted; java.io.NotSerializableException: myROI
Again Google tells me myROI
needs to implements Serializable
. I tried just adding implements Serializable
to the class definition, but it is not sufficient. Can anyone give me some hints on how to procede in this case? Also, how to get rid of the typecast warning?
warning: [unchecked] unchecked cast found
This is innocent and should indeed be fixed using @SuppressWarnings("unchecked")
annotation.
<identifier> expected
This can impossibly be caused by adding the annotation. Probably you added it at the wrong place (should be right before method declaration), or you did something else which caused that the declaration of ROIs
disappeared.
java.io.NotSerializableException: myROI
This means that the class identified by the given full qualified class name is not serializable. Expect from that it is not serializable, there's another serious problem: that class is not inside a package. This is not necessarily the cause of the current problem, but this may lead to future problems because packageless classes are invisible for classes inside a package.
To make a class serializable you need to let it implements Serializable
and ensure that all fields are serializable as well. Primitives are by default serializable and String
itself already implements it as you can read in its Javadoc. If a field really cannot be made serializable for some reason, then you need to declare it transient
and if necessary override private void readObject()
and private void writeObject()
accordingly so that the unserializable object can be written/read to the steam anyway. To the point, you just need to save its state in some way that exactly the same state can be restored afterwards.
E.g.
public class SerializableObject implements Serializable {
private transient UnserializableObject unserializableObject;
private void writeObject(ObjectOutputStream oos) throws IOException {
oos.defaultWriteObject();
oos.writeObject(unserializableObject.getSerializableProperty());
oos.writeObject(unserializableObject.getAnotherSerializableProperty());
// ...
}
private void readObject(ObjectInputStream ois) throws ClassNotFoundException, IOException {
ois.defaultReadObject();
unserializableObject = new UnserializableObject();
unserializableObject.setSerializableProperty((SomeSerializableObject) ois.readObject());
unserializableObject.setAnotherSerializableProperty((AnotherSerializableObject) ois.readObject());
// ...
}
}
Every attribute of myROI must implement Serializable or must be a simple datatype like int. Is this so?
精彩评论