一.对象序列化:
1).将对象转换为字节流保存起来,并在以后还原这个对象,这种机制就叫做序列化。
2).将一个对象保存到永久存储设备上称为持久化。
3).如果一个对象想要实现序列化,必须实现Serializable接口或Externalizable接口。
4).当一个对象被序列化,只保存对象的非静态成员变量,不能保存任何成员方法和静态的成员变量。
5).如果一个对象的成员变量是一个对象,那么这个对象的数据成员也会被保存。
6).如果一个可序列化对象包含对某个不可序列化的对象引用,那么整个序列化操作都会失败,会抛出一个NotSerializableException.我们可以将不需要或无法进行序列化的引用标记为transient,这个引用在序列化是就不会被序列化,所以这个可序列化对象可以完成序列化。
7).声明成transient的变量不被序列化工具存储,同样static变量也不会被存储。
二.序列化实现:
<span style="font-size:18px;">public class SerializableTest { public static void main(String[] args) throws Exception { Person p1 = new Person("赵三",18,1.88); Person p2 = new Person("李四",28,1.77); Person p3 = new Person("王五",38,1.66); FileOutputStream fos = new FileOutputStream("person.txt"); //对象输出流 ObjectOutputStream oos = new ObjectOutputStream(fos); oos.writeObject(p1); oos.writeObject(p2); oos.writeObject(p3); oos.close(); } } class Person implements Serializable{ String name; int age; double height; public Person(String name , int age ,double height){ this.name = name ; this.age = age; this.height = height; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public double getHeight() { return height; } public void setHeight(double height) { this.height = height; } }</span>
在项目目录下就会有一个person.txt文件,里面保存着对象的二进制数据。
如果其中有不想保存的变量可以这样:
transient String name;
这样name这个成员变量就不会被保存了。
三.反序列化实现:
public class SerializableTest { public static void main(String[] args) throws Exception { Person p1 = new Person("赵三",18,1.88); Person p2 = new Person("李四",28,1.77); Person p3 = new Person("王五",38,1.66); FileOutputStream fos = new FileOutputStream("person.txt"); //对象输出流 ObjectOutputStream oos = new ObjectOutputStream(fos); oos.writeObject(p1); oos.writeObject(p2); oos.writeObject(p3); oos.close(); FileInputStream fis = new FileInputStream("person.txt"); ObjectInputStream ois = new ObjectInputStream(fis); Person p = null ; for(int i = 0 ; i < 3 ; i++){ p = (Person)ois.readObject(); System.out.println(p.getName()+" "+p.getAge()+" "+p.getHeight()); } ois.close(); } } class Person implements Serializable{ String name; int age; double height; public Person(String name , int age ,double height){ this.name = name ; this.age = age; this.height = height; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public double getHeight() { return height; } public void setHeight(double height) { this.height = height; } }
打印:
赵三 18 1.88
李四 28 1.77
王五 38 1.66
四.实现自己定义的序列化方法:
在序列化和反序列化中实现了下面两个方法:
private void writeObject(ObjectOutputStream out) throws IOException{ out.writeUTF(name); out.writeInt(age); } private void readObject(ObjectInputStream in) throws IOException,ClassNotFoundException{ this.name = in.readUTF(); this.age = in.readInt(); }
我们就可以以更加底层,更加细粒度的方式控制序列化和反序列化的过程。
具体实现:
<span style="font-size:18px;">public class SerializableTest { public static void main(String[] args) throws Exception { Person p1 = new Person("赵三",18,1.88); Person p2 = new Person("李四",28,1.77); Person p3 = new Person("王五",38,1.66); FileOutputStream fos = new FileOutputStream("person.txt"); //对象输出流 ObjectOutputStream oos = new ObjectOutputStream(fos); oos.writeObject(p1); oos.writeObject(p2); oos.writeObject(p3); oos.close(); FileInputStream fis = new FileInputStream("person.txt"); ObjectInputStream ois = new ObjectInputStream(fis); Person p = null ; for(int i = 0 ; i < 3 ; i++){ p = (Person)ois.readObject(); System.out.println(p.getName()+" "+p.getAge()+" "+p.getHeight()); } ois.close(); } } class Person implements Serializable{ String name; int age; double height; public Person(String name , int age ,double height){ this.name = name ; this.age = age; this.height = height; } private void writeObject(ObjectOutputStream out) throws IOException{ out.writeUTF(name); out.writeInt(age); } private void readObject(ObjectInputStream in) throws IOException,ClassNotFoundException{ this.name = in.readUTF(); this.age = in.readInt(); } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public double getHeight() { return height; } public void setHeight(double height) { this.height = height; } }</span>
打印:
赵三 18 0.0
李四 28 0.0
王五 38 0.0