我理解的serialVersionUID

在创建一个实现了序列化接口的class的时候,都会提示你创建一个serialVersionUID (如果你不显示的创建,则jvm会自动创建一个,但是这个id会根据不同的jvm创建不同的id,不推荐)这个到底有什么作用呢?

作用主要用在反序列化的时候,java在做反序列化的时候,将相同serialVersionUID 的类认定为同一个类,这个serialVersionUID 有两种生成方式:

1,采用默认的:比如:`private static final long serialVersionUID = 1L; (这个暂时不太理解,就暂认定为默认值吧)

2,采用生成的:结合类名,方法名,属性及类型产生的一个哈希代码;

有的公司的项目,就是从原来的项目里copy过去,所以`serialVersionUID 也没改,这样的话,当你修改了属性,或者方法后,当java在反序列化的时候,就会认定你和之前的类是同一个对象。这样的话,在本地运行是好的,但是放到tomcat上就抛出javax.servlet.ServletException: BeanUtils.populate 错误。
类A:

public class A implements Serializable{
    private static final long serialVersionUID = 1L;

    String name;
    //set get 方法省略

}

WriteObject

pubic class Test{
    A a = new A();
    a.setName("a1");
    FileOutputStream out = new FileOutputStream(new File("D://1.txt"));
    ObjectOutput b = new ObjectOutputStream(out);
    b.writeObject(t1);
    b.flush();
    b.close();
}

ReadObject

public class Test2{
        ObjectInput in = new ObjectInputStream(new FileInputStream(new File("D://1.txt")));
        A a = (A) in.readObject();
        in.close();
        System.out.println(a.getName());
}

举个例子:创建一个A类,假设serialVersionUID 为1L,然后创建一个实例a,你把这个类序列化写到本地磁盘的1.txt文件中,然后,你在从1.txt中读取A,也就是对A进行反序列化,如果有以下的操作,则会抛出不一样的错误:

1,没有serialVersionUID ,但是做了一些不兼容的操作(具体哪些是属于不兼容的操作,见文章末尾),比如最简单的,删除了name属性,然后你再运行readObject的操作,就会报错,incompatible types for field name

2,修改serialVersionUID :比如修改为2L,运行readObject操作,会抛出:local class incompatible: stream classdesc serialVersionUID = 1, local class serialVersionUID = 2

附件,不兼容操作

  • 删除属性 - 如果一个类中的某个属性被删除, 那么流的写操作就不会保留那个属性. 当用以前的类来进行流的读取操作的话, 由于流里没有那个属性,这个值就会被设为一个默认值(比如null等)。
  • 移动类的继承等级 - 由于数据会出现在不同的序列中,所以这种情况也是不允许的。
  • 将nonstatic 属性 更改为 static,或者将 nontransient 属性更改为 transient - 当使用默认的序列化时, 这个操作等同于删除一个属性。
  • 更改属性的声明类型 - 每个版本的类会根据他声明的类型来读写属性,所以当声明类型不一致的时候,会报错.
  • 重写writeObject 或者 readObject 方法
  • 将序列化的类修改为非序列化类
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值