在Java中实现对象反序列化非常简单,实现java.io.Serializable(内部序列化)或java.io.Externalizable(外部序列化)接口即可被序列化,其中java.io.Externalizable接口只是实现了java.io.Serializable接口。
反序列化类对象时有如下限制:
- 被反序列化的类必须存在。
serialVersionUID值必须一致。
除此之外,反序列化类对象是不会调用该类构造方法的,因为在反序列化创建类实例时使用了sun.reflect.ReflectionFactory.newConstructorForSerialization创建了一个反序列化专用的Constructor(反射构造方法对象),使用这个特殊的Constructor可以绕过构造方法创建类实例(前面章节讲sun.misc.Unsafe 的时候我们提到了使用allocateInstance方法也可以实现绕过构造方法创建类实例)。
使用反序列化方式创建类实例代码片段:
package com.anbai.sec.serializes;import sun.reflect.ReflectionFactory;import java.lang.reflect.Constructor;/*** 使用反序列化方式在不调用类构造方法的情况下创建类实例* Creator: yz* Date: 2019/12/20*/public class ReflectionFactoryTest {public static void main(String[] args) {try {// 获取sun.reflect.ReflectionFactory对象ReflectionFactory factory = ReflectionFactory.getReflectionFactory();// 使用反序列化方式获取DeserializationTest类的构造方法Constructor constructor = factory.newConstructorForSerialization(DeserializationTest.class, Object.class.getConstructor());// 实例化DeserializationTest对象System.out.println(constructor.newInstance());} catch (Exception e) {e.printStackTrace();}}}
程序运行结果:
com.anbai.sec.serializes.DeserializationTest@2b650cea
具体细节可参考 不用构造方法也能创建对象。
