序列化就是將object轉(zhuǎn)為byte序列,反之叫做反序列化。
- 序列化流(ObjectOutputStream):是過濾流,主要方法writeObject
- 反序列化流(ObjectInputStream):readObject
- 序列化接口(Serializable):對(duì)象必須實(shí)現(xiàn)序列化接口才能進(jìn)行序列化。這個(gè)接口沒有任何方法,但是卻是必須的規(guī)定。
public class Student implements Serializable{
private String studentName;
private String studentAge;
private String studentNum;
...
String file = "./fileIOTestFileFolder/obj.txt";
public void objectToBytes() throws IOException{
ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream(file));
Student studentZhang = new Student("zhang","21","001");
objectOutputStream.writeObject(studentZhang);
objectOutputStream.close();
System.out.println("finish object to bytes. result in obj.txt");
}
public void bytesToObject() throws IOException, ClassNotFoundException {
ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream(file));
Student studentZhang = (Student)objectInputStream.readObject();
System.out.println(studentZhang);
objectInputStream.close();
}
transient關(guān)鍵字
object中,擁有該關(guān)鍵字的屬性不會(huì)被jvm默認(rèn)的序列化。但是可以隨后自行序列化。
public class Student implements Serializable{
private String studentAge;
private String studentNum;
private transient String studentName;
...
private void writeObject(java.io.ObjectOutputStream s) throws java.io.IOException{
s.defaultWriteObject();
s.writeObject(studentName);//自行完成studentName序列化
}
private void readObject(java.io.ObjectInputStream s) throws java.io.IOException, ClassNotFoundException {
s.defaultReadObject();
this.studentName =(String)s.readObject();//自行完成studentName反序列化
}
}
其中default為進(jìn)行JVM默認(rèn)的序列化操作。
transient 關(guān)鍵字乍一看很雞肋,使得我們需要將原本自動(dòng)完成的內(nèi)容進(jìn)行手都編寫序列化,但是transient 可以提高序列化的性能。對(duì)于一些特殊的對(duì)象,比如對(duì)象中的一個(gè)未滿的數(shù)組。如果自動(dòng)序列化,則該數(shù)組會(huì)全部序列化,但是如果我們的數(shù)組只使用了一半,則有一半不需要的部分被序列化了。
java ArrayList的源碼內(nèi)可以看到相關(guān)的一些操作。
序列化過程中存在子類父類關(guān)系時(shí),對(duì)子類對(duì)象進(jìn)行反序列化時(shí)如果其父類沒有實(shí)現(xiàn)序列化接口,則其父類的構(gòu)造函數(shù)將會(huì)被顯式調(diào)用。