先来说一下什么是序列化与反序列化?
序列化:
永久的保存对象,保存对象的字节序列到本地文件中
反序列化:
将保存到本地文件中的对象读取到内存中,还原成这个对象
如何实现序列化与反序列化?
一个类如果想被序列化,则必须实现java.io.Serializable接口,这个接口没有定义任何方法,是一个标志性接口,当一个类实现了该接口,就表示这个类的对象是可以被序列化的
下面说一下序列化的时候,需要注意的问题
1.当一个对象被序列化的时候,只保存对象的非静态成员变量,因为静态成员与方法是属于类的成员
2.如果一个对象的成员变量是一个对象,那么这个对象的数据成员也会被保存
3.如果一个可序列化对象包含了某个不可序列化对象的引用,那么整个序列化是会失败的,并且会抛出一个NotSerializableException,我们可以将这个引用标记为transient,表示为短暂的,此时该变量就无法被序列化,然后对象依旧可以被序列化
下面介绍一下序列化与反序列化用到的两个对象与方法
1.序列化对象与方法

上面序列化是要把对象写出去,因此就要用到ObjectOutputStream流
这里还需要说明一点的就是,序列化一般在外部存储文件,该文件的扩展名一般就叫.ser
2.反序列化的对象与方法


下面我们来看代码实例
先来看我们需要序列化的一个类
Person
- package domain;
-
- import java.io.Serializable;
- import java.util.Date;
-
- public class Person implements Serializable {
- String name;
- int age;
- String gender;
- //添加了一个短暂属性,表明这个字段不可别序列化
- transient Date birthday;
-
- public Date getBirthday() {
- return birthday;
- }
-
- public void setBirthday(Date birthday) {
- this.birthday = birthday;
- }
-
- 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 String getGender() {
- return gender;
- }
-
- public void setGender(String gender) {
- this.gender = gender;
- }
- }
序列化类SerializeTest1.java
- package test;
-
- import domain.Person;
-
- import java.io.FileNotFoundException;
- import java.io.FileOutputStream;
- import java.io.IOException;
- import java.io.ObjectOutputStream;
- import java.util.Date;
-
- public class SerializeTest1 {
- public static void main(String[] args) throws IOException {
- Person p = new Person();
- p.setName("王二麻子");
- p.setAge(520);
- p.setGender("男");
- p.setBirthday(new Date());
- //建立一个序列化对象
- FileOutputStream fis = new FileOutputStream("D:/w.ser");
- ObjectOutputStream oos = new ObjectOutputStream(fis);
- oos.writeObject(p);
- oos.close();
- fis.close();
- }
- }
这个就会在指定位置给我们产生一个文件

但是你不要打开这个看啊,因为这个肯定是乱码,毕竟是一个序列化文件,属于正常情况
然后去看我们的反序列化文件Deserialize.java
- package test;
-
- import domain.Person;
-
- import java.io.*;
-
- public class DeserializeTest1 {
- public static void main(String[] args) {
- //将文件进行反序列化
- Person p = null;
- //建立一个反序列化对象
- //这里是.ser序列化的文件
- FileInputStream fis = null;
- ObjectInputStream objectInputStream = null;
- try {
- fis = new FileInputStream("D:/w.ser");
- objectInputStream = new ObjectInputStream(fis);
- p = (Person) objectInputStream.readObject();
- } catch (Exception e) {
- e.printStackTrace();
- }finally{
- try {
- objectInputStream.close();
- } catch (IOException e) {
- e.printStackTrace();
- } finally {
- try {
- fis.close();
- } catch (IOException e) {
- e.printStackTrace();
- }
- }
- }
-
- //上面就会反序列化之前我们在文件中存放的对象
- //然后访问一下之前创建的对象
- System.out.println("Name: " + p.getName());
- System.out.println("age: " + p.getAge());
- System.out.println("gender: " + p.getGender());
- System.out.println("birthday: " + p.getBirthday());
- }
- }
运行结果:

这里在说一下为什么birthday是NULL,不是之前设置了值吗?你忘啦,我们添加了transient短暂属性,所以它不会被序列化的。
再见。