Java SerialVersionUID作用详解

 更新时间:2021年08月12日 11:12:02   作者:wy_erhu  
这篇文章主要介绍了Java SerialVersionUID作用详解,本篇文章通过简要的案例,讲解了该项技术的了解与使用,以下就是详细内容,需要的朋友可以参考下

问题1:Serializable是什么

首先,说说Serializable是实现java将内存中的类存储至硬盘中而使用的

一个类使用了Serializalbe接口,在序列化到文件时,会有一个SerialVersionUID。

这个东东是用于对类进行版本控制的。

首先看Person类清单:

=====

import  java.io.Serializable;
 
public  class  Person  implements  Serializable {
     
     //如果没有指定serialVersionUID,系统会自动生成一个
     private  static  final  long  serialVersionUID = 1L;
     private  String name;
     //添加这么一个成员变量  
     private  String address;    //序列化后如果之前版本没有,就为null
 
     public  String getName() {
//      int a = 100;
//      for(int i=0;i<a;i++){
//          name+=i;
//      }
         return  name;
     }
     public  void  setName(String name) {
         this .name = name;
     }
}

===== 然后是测试类清单 =====

import  java.io.FileInputStream;
import  java.io.FileNotFoundException;
import  java.io.FileOutputStream;
import  java.io.IOException;
import  java.io.ObjectInputStream;
import  java.io.ObjectOutputStream;
 
/**
  * if Object implements Serializable without Uid,
  * system will automatically give this object a uid by algorithm
  * @author v11
  * @date 2014年9月18日
  * @version 1.0
  */
public  class  WhySerialversionUID {
 
     public  static  void  objectToFile(Object obj,String fileName)  throws  Exception{
         ObjectOutputStream oo =  new  ObjectOutputStream( new  FileOutputStream(
                 fileName));
         oo.writeObject(obj);
         oo.close();
     }
 
     public  static  Object getObjectFromFile(String fileName)  throws  Exception {
         ObjectInputStream oi =  new  ObjectInputStream( new  FileInputStream(
                 fileName));
         Person crab_back = (Person) oi.readObject();
         oi.close();
         return  crab_back;
     }
     public  static  void  main(String[] args)  throws  Exception {
         String fileName =  "crab_file" ; //文件名
         
         // 这里是把对象序列化到文件
         Person crab =  new  Person();
         crab.setName( "Mr.Crab" );
         
         //储存到文件中
         //objectToFile(crab,fileName);
 
         // 这里是把对象序列化到文件,我们先注释掉,一会儿用
         Person crabBack = (Person) getObjectFromFile(fileName);
         //Dog crabBack = (Dog) getObjectFromFile(fileName);
         System.out.println( "Hi, My name is "  + crabBack.getName());
 
     }
}

=====

1.对于Person类中,将变量 address和SerialVersionUID注释掉,存储到文件,并读出。显示正常

2.将变量address还原,读取原来存储的文件,显示异常。抛出错误 InvalidClassException。

原因如下:

因为我们没有指定SerialVersionUID,因此系统自动生成了一个serialVersionUID(这个是根据类名,变量名,方法名)生成的

但是改动后的Person中变量名有变动,于是这个UID就不一样了,对于版本控制就无法读取。

所以,大家在很多代码里看到把UID设置为1L,就是Person代码中那样。

将Person代码UID设置为1L,再重复上述步骤,不报错。那么就意味着如果你选择将UID设置为1L,就是选择了兼容类的版本不一致。

PS:为什么说自动生成的 serialVersionUID是根据 类名,变量名,方法名,因为当你在原有的类的方法内进行添加内容,并不是对最后系统生成的UID造成影响,即不会抛出错误

问题2:所有类都设置为1L,是否有不良影响,不同类会不会冲突

public  class  Dog  implements  Serializable{
     
     private  static  final  long  serialVersionUID = 1L;
     private  String name;
     
     public  String getName() {
         return  name;
     }
 
     public  void  setName(String name) {
         this .name = name;
     }
     
}

新定义Dog类如上,将测试类代码中Dog的赋值注释去掉

 //Dog crabBack = (Dog) getObjectFromFile(fileName);

运行结果抛出错误:

Exception in thread "main" java.lang.ClassCastException: serializable.Person cannot be cast to serializable.Dog

说明serializable在不同类一间并不矛盾。

到此这篇关于Java SerialVersionUID作用详解的文章就介绍到这了,更多相关Java SerialVersionUID内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Java NIO 中Buffer 缓冲区解析

    Java NIO 中Buffer 缓冲区解析

    这篇文章主要介绍了Java NIO 中Buffer 缓冲区,Java NIO 中的 Buffer 用于和 NIO 通道进行交互。数据是通道读取到缓冲区,从缓冲区写入到通道中的。下面内容希望帮助带大家理解
    2022-02-02
  • spring中@Configuration和@Bean注解的用法

    spring中@Configuration和@Bean注解的用法

    这篇文章主要介绍了spring中@Configuration和@Bean注解的用法,@Configuration用于定义配置类,可替换xml配置文件,被注解的类内部包含有一个或多个被@Bean注解的方法,需要的朋友可以参考下
    2023-05-05
  • SpringBoot使用注解进行分页的实现示例

    SpringBoot使用注解进行分页的实现示例

    分页使用可以说非常普遍了,有时候会需要非常灵活的方式去开启或关闭分页,尝试使用一下注解的方式来进行分页,本文主要介绍了SpringBoot使用注解进行分页的实现示例,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-03-03
  • Java 生成随机单据号的实现示例

    Java 生成随机单据号的实现示例

    本文主要介绍了Java 生成随机单据号的实现示例,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-09-09
  • Java中的MapStruct用法详解

    Java中的MapStruct用法详解

    这篇文章主要介绍了Java中的MapStruct用法详解,MapStuct的使用非常简单,把对应的jar包引入即可,本文通过示例代码给大家介绍的非常详细,需要的朋友可以参考下
    2022-04-04
  • 如何通过自定义spring invalidator注解校验数据合法性

    如何通过自定义spring invalidator注解校验数据合法性

    这篇文章主要介绍了如何通过自定义spring invalidator注解校验数据合法性,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-07-07
  • Intellij IDEA 的maven项目通过Java代码实现Jetty的Http服务器(推荐)

    Intellij IDEA 的maven项目通过Java代码实现Jetty的Http服务器(推荐)

    Jetty是一个轻量级的高度可扩展的基于 java的web服务器和servlet引擎,这篇文章主要介绍了Intellij IDEA 的maven项目通过Java代码实现 Jetty 的 Http服务器从而获取到 Http 的 Get 和 Post 请求,需要的朋友可以参考下
    2022-07-07
  • springboot 去掉netflix 禁用Eureka的解决方法

    springboot 去掉netflix 禁用Eureka的解决方法

    这篇文章主要介绍了springboot 去掉netflix 禁用Eureka的解决方法,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2023-09-09
  • java Hibernate save()与persist()区别

    java Hibernate save()与persist()区别

    本文章来给各位同学介绍一下Hibernate save()与persist()区别,希望此文章能对各位同学对于Hibernate save()与persist()有所理解
    2016-01-01
  • 基于java+springboot+mybatis+laiyu实现学科竞赛管理系统

    基于java+springboot+mybatis+laiyu实现学科竞赛管理系统

    这篇文章主要介绍了基于java+springboot+mybatis+laiyu实现的学科竞赛管理系统,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-09-09

最新评论