2011年计算机等级考试二级JAVA学习(16)
![](http://www.onekao.net/templets/default/images/content_ad.gif)
#
1.1.3.1.4 序列化再探讨
从以上技术的讨论中我们不难体会到,序列化是Java之所以能够出色地实现其鼓吹的两大卖点??分布式(distributed)和跨平台(OS independent)的一个重要基础。TIJ(即“Thinking in Java”)谈到I/O系统时,把序列化称为“lightweight persistence”??“轻量级的持久化”,这确实很有意思。
#
★为什么叫做“序列”化? #
开场白里我说更习惯于把“Serialization”称为“序列化”而不是“串行化”,这是有原因的。介绍这个原因之前先回顾一些计算机基本的知识,我们知道现代计算机的内存空间都是线性编址的(什么是“线性”知道吧,就是一个元素只有一个唯一的“前驱”和唯一的“后继”,当然头尾元素是个例外;对于地址来说,它的下一个地址当然不可能有两个,否则就乱套了),“地址”这个概念推广到数据结构,就相当于“指针”,这个在本科低年级大概就知道了。注意了,既然是线性的,那“地址”就可以看作是内存空间的“序号”,说明它的组织是有顺序的,“序号”或者说“序列号”正是“Serialization”机制的一种体现。为什么这么说呢?譬如我们有两个对象a和b,分别是类A和B的实例,它们都是可序列化的,而A和B都有一个类型为C的属性,根据前面我们说过的原则,C当然也必须是可序列化的。 #
1. import java.io.*; #
2. ... #
3. class A implements Serializable #
4. {
5. C c; #
6. ... #
7. } #
8. #
9. class B implements Serializable
10. {
11. C c;
12. ...
#
13. } #
14.
15. class C implements Serializable
16. {
17. ...
18. }
#
19. #
20. A a; #
21. B b;
22. C c1; #
23. ...
#
注意,这里我们在实例化a和b的时候,有意让他们的c属性使用同一个C类型对象的引用,譬如c1,那么请试想一下,但我们序列化a和b的时候,它们的c属性在外部字节流(当然可以不仅仅是文件)里保存的是一份拷贝还是两份拷贝呢?序列化在这里使用的是一种类似于“指针”的方案:它为每个被序列化的对象标上一个“序列号”(serial number),但序列化一个对象的时候,如果其某个属性对象是已经被序列化的,那么这里只向输出流写入该属性的序列号;从字节流恢复被序列化的对象时,也根据序列号找到对应的流来恢复。这就是“序列化”名称的由来!这里我们看到“序列化”和“指针”是极相似的,只不过“指针”是内存空间的地址链,而序列化用的是外部流中的“序列号链”。
使用“序列号”而不是内存地址来标识一个被序列化的对象,是因为从流中恢复对象到内存,其地址可能就未必是原来的地址了??我们需要的只是这些对象之间的引用关系,而不是死板的原始位置,这在RMI中就更是必要,在两台不同的机器之间传递对象(流),根本就不可能指望它们在两台机器上都具有相同的内存地址。
#