关闭

java 序列化学习笔记

269人阅读 评论(0) 收藏 举报

什么是序列化?

它是JAVA为了将对象写入到文件中产生的机制,也就是只有在对象数据流中才能用到,目的就是为了从文件中读取或者记录对象。

 

序列化就是将对象写入到“硬盘”中,该对象必须继承Serializable接口(不用实现任何方法),这个接口仅仅起到标记的作用
eg: public class Person implements Serializable{}


静态属性是不能被序列化的,因为它在“堆”中

 

因为序列化是RMI过程的参数和返回值都必须实现的机制,而RMI又是java ee技术的基础——所有分布式应用常常需要跨平台、跨网络,所以要求所有传递的参数、返回值必须实现序列化。因此序列化机制是Java EE平台基础。通常建议:程序创建每个JavaBean类都实现Serializable。

 

如果需要将某个对象保存到磁盘上或者通过网络传输,那么这个对象需要序列化,即实现Serializable接口或者Externalizable接口。

 

反序列化读取的仅仅是Java对象的数据,而不是java类,因此采用反序列化恢复java对象时,必须提供该java对象所属类的class文件,否则会引发ClassNotFoundException异常。

反序列化机制无须通过构造器来初始化Java对象。

 

如果使用序列化机制向文件中写入多个java对象,使用反序列化机制恢复对象时必须按照实际写入的顺序读取。

 

当一个可序列化类有多个父类时(包括直接父类和间接父类),这些父类要么有无参数的构造器,要么也是可序列化的——否则反序列化时将抛出InvalidClassExcepiton异常。如果父类是不可序列化的,只是带有无参数的构造器,则该父类中定义的Field值不会序列化到二进制中。

 

如果某个类的Field类型不是基本类型或String类型,而是另一个引用类型,那么这个引用类型必须是可序列化的,否则拥有该类型的Field的类也是不可序列化的。

 

Java序列化机制采用了一种特殊的序列化算法:

1、所有保存到磁盘中的对象都有一个序列化编号

2、当程序试图序列化一个对象时,程序将先检查该对象是否已经被序列化过,只有该对象从未(在本次虚拟机中)被序列化过,系统才会将该对象转换成字节序列并输出。

3、如果某个对象已经序列化过,程序将只是直接输出一个序列化编号,而不是再次重新序列化该对象。

 

如果多次序列化同一个Java对象,只有第一次序列化时才会把该java对象转换成字节序列并输出,这样可能引起一个潜在的问题——当程序序列化一个可变对象时,只有第一次使用writeObject()方法输出时才会将该对象转换成字节序列并输出,当程序再次调用writeObject()方法时,程序只是输出前面的序列化编号,即使后面该对象的Field值已经改变,改变的Field值也不会被输出。

 

当对某个对象进行序列化时,系统会自动把该对象的所有Field依次进行序列化,如果某个Field引用到另一个对象,则被引用的对象也会被序列化,如果被引用的对象的Field也引用了其他对象,则被引用的对象也会被序列化,这种情况被称为递归序列化。

 

通过在Field前面使用transient关键字修饰,可以指定java序列化时无须理会该Field。

transient关键字只能用于修饰Field,不可修饰JAVA程序中其他的部分。

eg: transient int age;

 

序列化之后的文件名命名规则:对象名称.object;因为这个文件不是用来给用户看的,打开了里面全部是乱码,但是我们应该从文件名中可以看出这个文件是存储的什么东西,作用是什么,所以文件名尤为重要

读写对象的方法示例

 

ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("c:\\Person.object"));
oos.writeObject(new Person(20,"huangbiao"));
oos.close();

ObjectInputStream ois = new ObjectInputStream(new FileInputStream("c:\\Person.object"));
Person person = (Person)ois.readObject();

 

序列号是由属性、方法计算出来的,如果属性或者是方法改变,则序列号也变了,如果读对象要捕捉找不到类的异常,当然也可以指定对象的序列号,就能找到对象
eg: public static final long serializableUID = 42L;

0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:324447次
    • 积分:8899
    • 等级:
    • 排名:第2231名
    • 原创:1096篇
    • 转载:14篇
    • 译文:0篇
    • 评论:5条
    最新评论