Java: Serializzazione e interfaccia Externalizable
In Java è possibile trasformare un oggetto in un serie di byte (serializzazione) marcando la classe da serializzare come Serializable. java.io.Serializable è un inferfaccia “segnaposto” che non contiene metodi. Le classi che implementano quest’interfaccia indicano la possibilità di essere serializzate/deserializzate.
Di seguito un breve esempio:
import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; import java.io.Serializable; public class BaseExt { public static void main(String[] args) throws Throwable { new BaseExt().test(); } public void test() throws Throwable { String fileName = "C:/test.ser"; Box box = new Box("box1", new Dimension(20, 15, 30)); System.out.println("Writing box '" + box + "' to file: " + fileName + "..."); ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream(new File(fileName))); oos.writeObject(box); oos.flush(); oos.close(); // Box box1 = null; System.out.println("Reading box from file: " + fileName + "..."); ObjectInputStream ois = new ObjectInputStream(new FileInputStream(new File(fileName))); box1 = (Box)ois.readObject(); ois.close(); System.out.println(" Box readed: " + box1); } } class Dimension implements Serializable { private static final long serialVersionUID = 1141096386393987074L; public int x; public int y; public int z; public Dimension(int x, int y, int z) { this.x = x; this.y = y; this.z = z; } } class Box implements Serializable { private static final long serialVersionUID = -8550419011977999403L; private String id; private Dimension dim; public Box(String id, Dimension dim) { this.id = id; this.dim = dim; } @Override public String toString() { return String.format("%s <%d, %d, %d>", this.id, this.dim.x, this.dim.y, this.dim.z); } }
La classe Box viene serializzata e salvata su file per poi essere letta successivamente.
Java consente di avere più potere sul processo di serializzazione, mettendo a disposizione l’interfaccia Externalizable.
Durante il processo di serializzazione di una classe che implementa quest’interfaccia, solo l’identità della classe viene salvata ed è compito della classe stessa scrivere/leggere il contenuto dell’istanza, implementando i metodi readExternal e writeExternal
Il seguente è un semplice esempio di utilizzo:
import java.io.Externalizable; import java.io.File; 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; public class CustomExt { public static void main(String[] args) throws Throwable { new CustomExt().test(); } public void test() throws Throwable { String fileName = "C:/test.ser"; Box box = new Box("box1", new Dimension(20, 15, 30)); System.out.println("Writing externalizable box '" + box + "' to file: " + fileName + "..."); ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream(new File(fileName))); box.writeExternal(oos); oos.flush(); oos.close(); // Box box1 = new Box(); System.out.println("Reading externalizable box from file: " + fileName + "..."); ObjectInputStream ois = new ObjectInputStream(new FileInputStream(new File(fileName))); box1.readExternal(ois); ois.close(); System.out.println(" Box readed: " + box1); } } class Dimension { public int x; public int y; public int z; public Dimension(int x, int y, int z) { this.x = x; this.y = y; this.z = z; } } class Box implements Externalizable { private String id; private Dimension dim; public Box() { } public Box(String id, Dimension dim) { this.id = id; this.dim = dim; } @Override public String toString() { return String.format("%s <%d, %d, %d>", this.id, this.dim.x, this.dim.y, this.dim.z); } @Override public void readExternal(ObjectInput input) throws IOException, ClassNotFoundException { this.id = input.readUTF(); this.dim = new Dimension(input.readInt(), input.readInt(), input.readInt()); } @Override public void writeExternal(ObjectOutput output) throws IOException { output.writeUTF(this.id); output.writeInt(this.dim.x); output.writeInt(this.dim.y); output.writeInt(this.dim.z); } }