java.io.InvalidClassException 异常解决, 实现Serializable接口的注意事项

解决方案: 在类中显式指定

private static final long serialVersionUID = 42L;

类实现序列化接口, 进行序列化反序列化的时候, 抛出 java.io.InvalidClassException 异常

java.io.InvalidClassException: com.xx.Xxx; local class incompatible: stream classdesc serialVersionUID = -783991920331, local class serialVersionUID = -331138183213

这个异常是由于反序列化时, 当前类的serialVersionUID 与 bytes中的类反序列化后的类的serialVersionUID 不同所致, 这个serialVersionUID 如果不在类中显式声明, 则是通过类名,方法名等诸多因素经过计算而得,理论上是一一映射的关系,也就是唯一的

JDK中Serializable接口的声明

The serialization runtime associates with each serializable class a version number, called a serialVersionUID, which is used during deserialization to verify that the sender and receiver of a serialized object have loaded classes for that object that are compatible with respect to serialization. If the receiver has loaded a class for the object that has a different serialVersionUID than that of the corresponding sender‘s class, then deserialization will result in an InvalidClassException. A serializable class can declare its own serialVersionUID explicitly by declaring a field named "serialVersionUID" that must be static, final, and of type long:

   ANY-ACCESS-MODIFIER static final long serialVersionUID = 42L;

If a serializable class does not explicitly declare a serialVersionUID, then the serialization runtime will calculate a default serialVersionUID value for that class based on various aspects of the class, as described in the Java(TM) Object Serialization Specification. However, it is strongly recommended that all serializable classes explicitly declare serialVersionUID values, since the default serialVersionUID computation is highly sensitive to class details that may vary depending on compiler implementations, and can thus result in unexpected InvalidClassExceptions during deserialization. Therefore, to guarantee a consistent serialVersionUID value across different java compiler implementations, a serializable class must declare an explicit serialVersionUID value. It is also strongly advised that explicit serialVersionUID declarations use the private modifier where possible, since such declarations apply only to the immediately declaring class--serialVersionUID fields are not useful as inherited members. Array classes cannot declare an explicit serialVersionUID, so they always have the default computed value, but the requirement for matching serialVersionUID values is waived for array classes

重要的几点:

1. 所有实现序列化的类, 都推荐显式声明序列化ID

2. 序列化ID的访问类型 推荐为 private, 因为只在自己内部被使用, 不会因为继承而流到子类

3. 数组是无法显示声明序列化ID的(比如String[], 你无法在其中声明serialVersionUID), 但是java的序列化也不会对数组对象进行serialVersionUID 的比较

时间: 2024-07-31 10:31:37

java.io.InvalidClassException 异常解决, 实现Serializable接口的注意事项的相关文章

java.io.NotSerializableException:异常

java.io.NotSerializableException:异常,创建的pojo类未实现Serializable接口,启动服务器会报此异常,但是貌似对代码功能没影响,或者说暂时未发现有什么影响. 要解决此异常,可通过实现该接口解决. import java.io.Serializable; public class DeptPojo implements Serializable{ private String deptId; private String deptName; privat

java.io.InvalidClassException local class incompatible: stream classdesc serialVersionUID

现象: java.io.InvalidClassException: com.engine.data.User; local class incompatible: stream classdesc serialVersionUID = -6012532569298149921, local class serialVersionUID = 6087477983556853561 解决方案: 将本地的序列化的类中的版本号(serialVersionUID )改成和远程中一样 从上列异常中可以看出

关于 java 上传,下载和导入报java.lang.IllegalStateException异常解决办法

java.lang.IllegalStateException异常解决办法 最近在使用response.sendRedirect()时出现如下错误:java.lang.IllegalStateException            org.apache.catalina.connector.ResponseFacade.sendRedirect(ResponseFacade.java:423) 经过分析.查看jdk文档终于找到解决的办法,在response.sendRedirect()方法后加

Android java.io.IOException异常情况整理

前言 目前android上的绝大多数项目还是由JAVA开发的,而java最常见的异常之一就是java.io.IOException,这个异常我们在android开发中也会经常遇到,这里整理了一些在Android开展法中常见的IOException情况,但在实际中,造成IOException异常的原因可能多种多样,这里我只整理了几种,欢迎大家留言讨论. open failed: EACCES (Permission denied) 根据报错信息可知是因为权限错误导致,解决办法有以下几种: 1.在A

sun.reflect.generics.reflectiveObjects.TypeVariableImpl cannot be cast to java.lang.Class异常解决方法

package com.wzs; import java.lang.reflect.ParameterizedType; public class T1<T> {     private Class classt;     public T1() {         ParameterizedType type = (ParameterizedType) this.getClass().getGenericSuperclass();         this.classt = (Class)

【Java】对象序列化中出现的java.io.StreamCorruptedException异常

今天在试验对象序列化,看到在类继承了Serializable接口,还有两个函数会在对象序列化及反序列化时默认自动执行,分别是writeObject和readObject. 进行了简单的试验,发现在在程序执行过程中出现了下述异常: java.io.StreamCorruptedException: invalid type code: 00 at java.io.ObjectInputStream.readClassDesc(ObjectInputStream.java:1520) at java

Java实体对象为什么要实现Serializable接口?

前言 Java实体对象为什么一定要实现Serializable接口呢?在学JavaSE的时候有些实体对象不实现Serializable不是也没什么影响吗? 最近在学习mybatis的时候发现,老师写的实体对象都实现了Serializable接口,我查了查网上说是实现Serilizable接口是为了序列化 先来看下Serializable接口 Serializable是java.io包中定义的.用于实现Java类的序列化操作而提供的一个语义级别的接口.Serializable序列化接口没有任何方法

探究java.io之I/O类和接口

基于流的I/O系统被打包到java.io包中,本系列介绍那些自Java最初发布以来就已提供且广泛使用的部分.然而,从1.4版本开始,Java添加了另一套I/O系统,被称为NIO(也就是new I/O系统的缩写).NIO被打包到java.nio及其子包中..随着JDK7的发布,Java对NIO的功能进行了极大扩展,并且NIO的使用也在朝预期方向增长.NIO系统将在后面再讲. 下面列出了java.io定义的I/O类: BufferedInputStream                      

使用ksoap2报java.io.EOFException异常问题解决方法

使用ksoap2调用WebService数据读取正常,但一直报异常: java.io.EOFException at libcore.io.Streams.readAsciiLine(Streams.java:203) at libcore.net.http.HttpEngine.readResponseHeaders(HttpEngine.java:560) at libcore.net.http.HttpEngine.readResponse(HttpEngine.java:813) at