JAVA的序列化问题

简介:

今天工作时发现一个序列化的问题:

基类(类A)没有实现序列化接口(Serializable),而子类(类B)实现了序列化接口,对子类对像进行序列化,然后反序列化,这里发现反序化后的对象在基类的中的很多属性都变成了null.
 
  1. public abstract class FirstLevel {//基类  
  2.     private Map map;  
  3.    
  4.     public FirstLevel(){  
  5.      System.out.println("first");  
  6.     }  
  7.     protected void init(){  
  8.        map = new HashMap(0);  
  9.     }  
  10.       
  11.     public Map getMap() {  
  12.        return map;  
  13.     }  
  14.     public void setMap(Map map) {  
  15.        this.map = map;  
  16.     }  
  17. }  
  18.    
  19. public class SecondLevel extends FirstLevel implements Serializable{  
  20.     public SecondLevel(){  
  21.        init();  
  22.        System.out.println("second");  
  23.     }  
  24. }  
  25.    
  26. public class Test {  
  27.     public static void main(String args[]) throws FileNotFoundException, IOException, ClassNotFoundException{  
  28.        System.out.println("before:");  
  29.        SecondLevel before = new SecondLevel();  
  30.        HashMap a = new HashMap();  
  31.        a.put("key""guojje");  
  32.        before.setMap(a);   
  33.          
  34.        ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("c:\\t.txt"));  
  35.        oos.writeObject(before);  
  36.        oos.close();  
  37.        System.out.println("after:");  
  38.        ObjectInputStream ois = new ObjectInputStream(new FileInputStream("c:\\t.txt"));  
  39.        SecondLevel after = (SecondLevel)ois.readObject();  
  40.        ois.close();  
  41.        System.out.println(after.getMap());  
  42.          
  43.     }  
  44. }  
 
 
输出:
before:
first
second
after:
first
null
这里map属性我是赋过值的,为什么变成NULL了吗,另外创建对像时调用FirstLevel ,
SecondLevel 两个构造函数,但是反序列化时也调用了FirstLevel的构造函数(理论上序列化是不用调用构造函数的)。
 
看来没有实现序列化接口的基类并没有真正的序列化与反序列化,而是借用其构造函数来实现对象的初始化(可以肯定得不到序列化时的属性值),因为FirstLevel的构造函数并没有初始化MAP成员,所以返回NULL。
 
查阅一些资料,JDK文档上这么说:
序列化操作不会写出没有实现 java.io.Serializable 接口的任何对象的字段。不可序列化的 Object 的子类可以是可序列化的。在此情况下,不可序列化的类必须有一个无参数构造方法,以便允许初始化其字段。在此情况下,子类负责保存和还原不可序列化的类的状态。
 
果然如此。
 
又一个问题(A>B表示B继承于A):
   A > B (Serializable)> C > D(Serializable) > E
反序列化E对象,会调用哪几个构造函数呢,答案是一个, A的. 因为其他类都从基类继承了Serializable接口,而A没有.
 
下一个问题,如果想完全的序列化E对象怎么办:
   在子类中(B,C,D,E都可)来序例化A类的成员,然后赋值上去,别无他法.

本文转自 anranran 51CTO博客,原文链接:http://blog.51cto.com/guojuanjun/589348
相关文章
|
29天前
|
存储 Java
【IO面试题 四】、介绍一下Java的序列化与反序列化
Java的序列化与反序列化允许对象通过实现Serializable接口转换成字节序列并存储或传输,之后可以通过ObjectInputStream和ObjectOutputStream的方法将这些字节序列恢复成对象。
|
6天前
|
存储 Java
Java编程中的对象序列化与反序列化
【9月更文挑战第12天】在Java的世界里,对象序列化与反序列化是数据持久化和网络传输的关键技术。本文将带你了解如何通过实现Serializable接口来标记一个类的对象可以被序列化,并探索ObjectOutputStream和ObjectInputStream类的使用,以实现对象的写入和读取。我们还将讨论序列化过程中可能遇到的问题及其解决方案,确保你能够高效、安全地处理对象序列化。
|
22天前
|
存储 Java
Java编程中的对象序列化与反序列化
【8月更文挑战第28天】在Java世界中,对象序列化与反序列化是数据持久化和网络传输的关键技术。本文将深入浅出地探讨这一过程,带你领略其背后的原理及应用,让你的程序在数据的海洋中自由航行。
|
29天前
|
XML 存储 JSON
【IO面试题 六】、 除了Java自带的序列化之外,你还了解哪些序列化工具?
除了Java自带的序列化,常见的序列化工具还包括JSON(如jackson、gson、fastjson)、Protobuf、Thrift和Avro,各具特点,适用于不同的应用场景和性能需求。
|
16天前
|
存储 Java
Java编程中的对象序列化与反序列化
【9月更文挑战第2天】在Java的世界里,对象序列化和反序列化就像是给数据穿上了一件隐形的斗篷。它们让数据能够轻松地穿梭于不同的系统之间,无论是跨越网络还是存储在磁盘上。本文将揭开这层神秘的面纱,带你领略序列化和反序列化的魔法,并展示如何通过代码示例来施展这一魔法。
14 0
|
1月前
|
存储 安全 Java
揭秘Java序列化神器Serializable:一键解锁对象穿越时空的超能力,你的数据旅行不再受限,震撼登场!
【8月更文挑战第4天】Serializable是Java中的魔术钥匙,开启对象穿越时空的能力。作为序列化的核心,它让复杂对象的复制与传输变得简单。通过实现此接口,对象能被序列化成字节流,实现本地存储或网络传输,再通过反序列化恢复原状。尽管使用方便,但序列化过程耗时且存在安全风险,需谨慎使用。
35 7
|
2月前
|
存储 安全 Java
day24:Java零基础 - 序列化与反序列化
【7月更文挑战第24天】🏆本文收录于「滚雪球学Java」专栏,专业攻坚指数级提升,希望能够助你一臂之力,帮你早日登顶实现财富自由🚀;同时,欢迎大家关注&&收藏&&订阅!持续更新中,up!up!up!!
32 1
|
2月前
|
存储 安全 Java
day23:Java零基础 - 反序列化
【7月更文挑战第23天】🏆本文收录于「滚雪球学Java」专栏,专业攻坚指数级提升,希望能够助你一臂之力,帮你早日登顶实现财富自由🚀;同时,欢迎大家关注&&收藏&&订阅!持续更新中,up!up!up!!
31 2
|
2月前
|
存储 安全 Java
day22:Java零基础 - 序列化
【7月更文挑战第22天】🏆本文收录于「滚雪球学Java」专栏,专业攻坚指数级提升,希望能够助你一臂之力,帮你早日登顶实现财富自由🚀;同时,欢迎大家关注&&收藏&&订阅!持续更新中,up!up!up!!
28 3
|
2月前
|
自然语言处理 安全 Java
Java演进问题之Substrate VM处理Java序列化如何解决
Java演进问题之Substrate VM处理Java序列化如何解决