《Java核心技术 卷Ⅱ 高级特性(原书第10版)》一2.4.5 版本管理

简介: 本节书摘来华章计算机《Java核心技术 卷Ⅱ 高级特性(原书第10版)》一书中的第2章 ,第2.4.5节,[美] 凯S.霍斯特曼(Cay S. Horstmann) 著陈昊鹏 译 更多章节内容可以访问云栖社区“华章计算机”公众号查看。

2.4.5 版本管理

如果使用序列化来保存对象,就需要考虑在程序演化时会有什么问题。例如,1.1版本可以读入旧文件吗?仍旧使用1.0版本的用户可以读入新版本产生的文件吗?显然,如果对象文件可以处理类的演化问题,那它正是我们想要的。
乍一看,这好像是不可能的。无论类的定义产生了什么样的变化,它的SHA指纹也会跟着变化,而我们都知道对象输入流将拒绝读入具有不同指纹的对象。但是,类可以表明它对其早期版本保持兼容,要想这样做,就必须首先获得这个类的早期版本的指纹。我们可以使用JDK中的单机程序serialver来获得这个数字,例如,运行下面的命令
image

如果在运行serialver程序时添加-show选项,那么这个程序就会产生下面的图形化对话框(参见图2-7)。

image

这个类的所有较新的版本都必须把serialVersionUID常量定义为与最初版本的指纹相同。
image

如果一个类具有名为serialVersionUID的静态数据成员,它就不再需要人工地计算其指纹,而只需直接使用这个值。
一旦这个静态数据成员被置于某个类的内部,那么序列化系统就可以读入这个类的对象的不同版本。
如果这个类只有方法产生了变化,那么在读入新对象数据时是不会有任何问题的。但是,如果数据域产生了变化,那么就可能会有问题。例如,旧文件对象可能比程序中的对象具有更多或更少的数据域,或者数据域的类型可能有所不同。在这些情况中,对象输入流将尽力将流对象转换成这个类当前的版本。
对象输入流会将这个类当前版本的数据域与被序列化的版本中的数据域进行比较,当然,对象流只会考虑非瞬时和非静态的数据域。如果这两部分数据域之间名字匹配而类型不匹配,那么对象输入流不会尝试将一种类型转换成另一种类型,因为这两个对象不兼容;如果被序列化的对象具有在当前版本中所没有的数据域,那么对象输入流会忽略这些额外的数据;如果当前版本具有在被序列化的对象中所没有的数据域,那么这些新添加的域将被设置成它们的默认值(如果是对象则是null,如果是数字则为0,如果是boolean值则是false)。
下面是一个示例:假设我们已经用雇员类的最初版本(1.0)在磁盘上保存了大量的雇员记录,现在我们在Employee类中添加了称为department的数据域,从而将其演化到了2.0版本。图2-8展示了将1.0版的对象读入到使用2.0版对象的程序中的情形,可以看到department域被设置成了null。图2-9展示了相反的情况:一个使用1.0版对象的程序读入了2.0版的对象,可以看到额外的department域被忽略。
image

这种处理是安全的吗?视情况而定。丢掉数据域看起来是无害的,因为接收者仍旧拥有它知道如何处理的所有数据,但是将数据域设置为null却有可能并不那么安全。许多类都费尽心思地在其所有的构造器中将所有的数据域都初始化为非null的值,以使得其各个方法都不必去处理null数据。因此,这个问题取决于类的设计者是否能够在readObject方法中实现额外的代码去订正版本不兼容问题,或者是否能够确保所有的方法在处理null数据时都足够健壮。

相关文章
|
1月前
|
开发框架 Java API
最新Java基础系列课程--Day13-高级特性(二)
最新Java基础系列课程--Day13-高级特性
|
5月前
|
算法 安全 Java
2023年Java核心技术第十三篇(篇篇万字精讲)
2023年Java核心技术第十三篇(篇篇万字精讲)
55 1
|
1月前
|
Java 程序员 API
最新Java基础系列课程--Day13-高级特性(三)
最新Java基础系列课程--Day13-高级特性
|
1月前
|
开发框架 Java 程序员
最新Java基础系列课程--Day13-高级特性(一)
最新Java基础系列课程--Day13-高级特性
|
2月前
|
开发框架 Java 程序员
最新Java基础系列课程--Day13-高级特性
最新Java基础系列课程--Day13-高级特性
|
2月前
|
存储 Java 编译器
《Java 核心技术卷1 基础知识》第三章 Java 的基本程序设计结构 笔记(下)
《Java 核心技术卷1 基础知识》第三章 Java 的基本程序设计结构 笔记
78 0
|
2月前
|
存储 自然语言处理 Java
《Java 核心技术卷1 基础知识》第三章 Java 的基本程序设计结构 笔记(上)
《Java 核心技术卷1 基础知识》第三章 Java 的基本程序设计结构 笔记
76 0
|
2月前
|
Oracle Java 关系型数据库
《Java 核心技术卷1 基础知识》第二章 Java 程序设计环境 笔记
《Java 核心技术卷1 基础知识》第二章 Java 程序设计环境 笔记
29 1
|
2月前
|
存储 Java 编译器
《Java 核心技术卷1 基础知识》第一章 Java程序设计概述 笔记
《Java 核心技术卷1 基础知识》第一章 Java程序设计概述 笔记
40 0
|
2月前
|
Java API 容器
资深Java大牛带你由基础到原理再到项目实战,轻松掌控核心技术
《Java编程的逻辑》致力于帮助读者真正理解Java编程。对于每个语言特性和API,不仅介绍其概念和用法,还分析了为什么要有这个概念,实现原理是什么,背后的思维逻辑是什么;对于类库,分析了大量源码,使读者不仅知其然,还知其所以然,以透彻理解相关知识点。
资深Java大牛带你由基础到原理再到项目实战,轻松掌控核心技术