Java 对象序列化和反序列化 (实现 Serializable 接口)

时间:2023-03-09 07:52:36
Java 对象序列化和反序列化 (实现 Serializable 接口)

序列化和反序列化的概念

  把对象转换为字节序列的过程称为对象的序列化

  把字节序列恢复为对象的过程称为对象的反序列化

  对象的序列化主要有两种用途:
  1) 把对象的字节序列永久地保存到硬盘上,通常存放在一个文件中;
  2) 在网络上传送对象的字节序列。

JDK类库中的序列化API

  java.io.ObjectOutputStream代表对象输出流,它的writeObject(Object obj)方法可对参数指定的obj对象进行序列化,把得到的字节序列写到一个目标输出流中。
  java.io.ObjectInputStream代表对象输入流,它的readObject()方法从一个源输入流中读取字节序列,再把它们反序列化为一个对象,并将其返回。
  只有实现了Serializable和Externalizable接口的类的对象才能被序列化。Externalizable接口继承自 Serializable接口,实现Externalizable接口的类完全由自身来控制序列化的行为,

  而仅实现Serializable接口的类可以 采用默认的序列化方式 。

  对象序列化包括如下步骤: 

    1) 创建一个对象输出流,它可以包装一个其他类型的目标输出流,如文件输出流;
  2) 通过对象输出流的writeObject()方法写对象。


  对象反序列化的步骤如下:

  1) 创建一个对象输入流,它可以包装一个其他类型的源输入流,如文件输入流;
  2) 通过对象输入流的readObject()方法读取对象。

示例:

新建一个Car 类

 package com.oukele.redis2.entity;

 import java.io.Serializable;

 public class Car implements Serializable {

     /*
* 编号
*/
private int id;
/*
* 车名
*/
private String name;
/*
* 车速
*/
private double speed; public Car(String name,double speed ){
this.name = name;
this.speed = speed;
} public Car(int id, String name, double speed) {
this.id = id;
this.name = name;
this.speed = speed;
} public int getId() {
return id;
} public void setId(int id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public double getSpeed() {
return speed;
} public void setSpeed(double speed) {
this.speed = speed;
} @Override
public String toString() {
return "Car{" +
"id=" + id +
", name='" + name + '\'' +
", speed=" + speed +
'}';
}
}

新建一个 SerializeUtil 类 (封装 序列化 和 反序列化 的方法,便于调用 )

 package com.oukele.redis2.util;

 import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream; public class SerializeUtil { /*
* 序列化
* */
public static byte[] serialize(Object object){
//序列化流 (输出流) --> 表示向一个目标 写入数据
ObjectOutputStream objectOutputStream =null;
//字节数组输出流
ByteArrayOutputStream byteArrayOutputStream = null;
try{
//创建一个缓冲区
byteArrayOutputStream = new ByteArrayOutputStream();
//将 对象 序列化成 字节后 输入缓冲区中
objectOutputStream = new ObjectOutputStream(byteArrayOutputStream);
//序列化 对象
objectOutputStream.writeObject(object);
//得 到 序列化字节
byte[] bytes = byteArrayOutputStream.toByteArray(); //清空输出流
objectOutputStream.flush();
//释放资源
objectOutputStream.close(); return bytes;
}catch (Exception e){
System.out.println("出现异常:"+e.getMessage());
}
return null;
} /*
* 反序列化
* */ public static <T> T deserialize(byte[] bytes,Class<T> clazz){
//字节数组
ByteArrayInputStream byteArrayInputStream = null;
try{
//将 得到的序列化字节 丢进 缓冲区
byteArrayInputStream = new ByteArrayInputStream(bytes);
//反序列化流 (输入流)--> 表示着从 一个 源头 读取 数据 , (读取 缓冲区中 的字节)
ObjectInputStream objectInputStream = new ObjectInputStream(byteArrayInputStream);
//反序化成 一个对象
return (T)objectInputStream.readObject();
}catch (Exception e){
System.out.println("出现异常:"+e.getMessage());
}
return null;
} }

测试:

         //序列化一个对象
byte[] serialize = SerializeUitl.serialize(new Car(2,"宝马",88.8));
//反序列化
Car deserialize = SerializeUitl.deserialize(serialize, Car.class);
System.out.println(deserialize);

测试结果:

Java 对象序列化和反序列化 (实现 Serializable 接口)

示例源码地址: