当一个父类实现Serializable接口后,他的子类都将自动的实现序列化。

以下验证了这一点:

package Serial;

import java.io.Serializable;

public class SuperC implements Serializable {//父类实现了序列化

int supervalue;

public SuperC(int supervalue) {

this.supervalue = supervalue;

}

public String toString() {

return "supervalue: "+supervalue;

}

}

public class SubC extends SuperC {//子类

int subvalue;

public SubC(int supervalue,int subvalue) {

super(supervalue);

this.subvalue=subvalue;

}

public String toString() {

return super.toString()+" sub: "+subvalue;

}

}

public class Test1 {

public static void main(String [] args){

SubC subc=new SubC(100,200);

FileInputStream in=null;

FileOutputStream out=null;

ObjectInputStream oin=null;

ObjectOutputStream oout=null;

try {

out = new FileOutputStream("Test1.txt");//子类序列化

oout = new ObjectOutputStream(out);

oout.writeObject(subc);

oout.close();

oout=null;

in = new FileInputStream("Test1.txt");

oin = new ObjectInputStream(in);

SubC subc2=(SubC)oin.readObject();//子类反序列化

System.out.println(subc2);

} catch (Exception ex){

ex.printStackTrace();

} finally{

…此处省略

}

}

}

运行结果如下:

supervalue: 100 sub: 200

可见子类成功的序列化/反序列化了。

怎管让子类实现序列化看起来是一件很简单的事情,但有的时候,往往我们不能够让父类实现Serializable接口,原因是有时候父类是抽象的(这并没有关系),并且父类不能够强制每个子类都拥有序列化的能力。换句话说父类设计的目的仅仅是为了被继承。

要为一个没有实现Serializable接口的父类,编写一个能够序列化的子类是一件很麻烦的事情。java docs中提到:

“To allow subtypes of non-serializable classes to be serialized, the subtype may assume responsibility for saving and restoring the state of the supertype's public, protected, and (if accessible) package fields. The subtype may assume this responsibility only if the class it extends has an accessible no-arg constructor to initialize the class's state. It is an error to declare a class Serializable if this is not the case. The error will be detected at runtime. ”

也就是说,要为一个没有实现Serializable接口的父类,编写一个能够序列化的子类要做两件事情:

其一、父类要有一个无参的constructor;

其二、子类要负责序列化(反序列化)父类的域。

我们将SuperC的Serializable接口去掉,而给SubC加上Serializable接口。运行后产生错误:

java.lang.Error: Unresolved compilation problem:

Serializable cannot be resolved or is not a valid superinterface

at Serial.SubC.(SubC.java:15)

at Serial.Test1.main(Test1.java:19)

Exception in thread "main"

果真如docs中所说的一样,父类缺少无参构造函数是不行的。

接下来,按照docs中的建议我们改写这个例子:

public abstract class SuperC {

int supervalue;

public SuperC(int supervalue) {

this.supervalue = supervalue;

}

public SuperC(){}//增加一个无参的constructor

public String toString() {

return "supervalue: "+supervalue;

}

}

public class SubC extends SuperC implements Serializable {

int subvalue;

public SubC(int supervalue,int subvalue) {

super(supervalue);

this.subvalue=subvalue;

}

public String toString() {

return super.toString()+" sub: "+subvalue;

}

private void writeObject(java.io.ObjectOutputStream out)

throws IOException{

out.defaultWriteObject();//先序列化对象

out.writeInt(supervalue);//再序列化父类的域

}

private void readObject(java.io.ObjectInputStream in)

throws IOException, ClassNotFoundException{

in.defaultReadObject();//先反序列化对象

supervalue=in.readInt();//再反序列化父类的域

}

}

运行结果证明了这种方法是正确的。在此处我们用到了writeObject/ readObject方法,这对方法如果存在的话,序列化时就会被调用,以代替默认的行为(以后还要探讨,先了解这么多)。我们在序列化时,首先调用了ObjectOutputStream的defaultWriteObject,它使用默认的序列化行为,然后序列化父类的域;反序列化的时候也一样。

归纳一下:

目的 行为

为一个实现Serializable接口的父类,编写一个能够序列化的子类 子类将自动的实现序列化

为一个没有实现Serializable接口的父类,编写一个能够序列化的子类 1, 父类要有一个无参的constructor;2, 子类要先序列化自身,然后子类要负责序列化父类的域

跟多参考:http://www.ibm.com/developerworks/cn/java/j-lo-serial/

java继承序列化_java中序列化之子类继承父类序列化相关推荐

  1. java图片序列化_Java中的强大武器——对象的序列化

    原标题:Java中的强大武器--对象的序列化 所谓对象序列化就是将对象的状态转换成字节流,以后可以通过这些值再生成相同状态的对象.这个过程也可以通过网络实现,可以先在Windows机器上创建一个对象, ...

  2. java 继承 意义_Java中继承,类的高级概念的知识点

    1.继承含义 在面向对象编程中,可以通过扩展一个已有的类,并继承该类的属性和行为,来创建一个新的类,这种方式称为继承(inheritance). 2.继承的优点 A.代码的可重用性 B.子类可以扩展父 ...

  3. java 异常继承树_java中的error与exception

    Error类和Exception类都继承自Throwable类. Error的继承关系: Exception的继承关系: 二者的不同之处: Exception: 1.可以是可被控制(checked) ...

  4. java中write方法作用_java中的封装,继承,多态,这3个在程序中起着重要作用

    一.封装 1. 封装概述 面向对象编程语言是对客观世界的模拟,客观世界里成员变量都是隐藏在对象内部的,外界无法直接操作和修改. 封装可以被认为是一个保护屏障,防止该类的代码和数据被其他类随意访问.要访 ...

  5. java有道_java中的各种流(老师的有道云笔记)

    内存操作流-字节 之前的文件操作流是以文件的输入输出为主的,当输出的位置变成了内存,那么就称为内存操作流.此时得使用内存流完成内存的输入和输出操作. 如果程序运行过程中要产生一些临时文件,可采用虚拟文 ...

  6. java list对象_JAVA中list

    Java 查找 List 中的最大值.最小值 Java 查找 List 中的最大值.最小值 java> List list = new ArrayList(); java.util.List l ...

  7. java list原理_Java中ArrayList实现原理

    前言 这个分类中,将会写写Java中的集合.集合是Java中非常重要而且基础的内容,因为任何数据必不可少的就是该数据是如何存储的,集合的作用就是以一定的方式组织.存储数据.这里写的集合,一部分是比较常 ...

  8. java 注解开发_Java中的注解到底是如何工作的?

    作者:人晓 www.importnew.com/10294.html 自Java5.0版本引入注解之后,它就成为了Java平台中非常重要的一部分.开发过程中,我们也时常在应用代码中会看到诸如@Over ...

  9. java list 结构_Java中常见数据结构List之ArrayList

    这里主要包含ArrayList和LinkedList. 关于Java中的集合内容, 感觉都已经被写烂了, 我这里主要是做个复习, 再从扒下源代码, 尽量用最直白的语言把里面的核心内容记录下来.仅此而已 ...

最新文章

  1. Python 查看本机WiFi密码
  2. 日历,日期类(copy)
  3. Java命令行运行参数说明大全--转
  4. 实战 :为自己的公号搭建一个数据运营指标体系
  5. visual studio 设计器不显示_面向国际市场的装置开发运维软件设计与实现
  6. css默认的font-size是什么意思,常用的css属性:font-size等
  7. 超有意思的代码注释_程序员搞笑的代码注释:谁的代码注释我都不服,就服你的...
  8. iOS 7状态栏在iPhone应用程序中恢复到iOS 6默认样式?
  9. JavaSE学习笔记--Item1 注解Annotation
  10. [Unity3D]ml-agent入门案例
  11. 背包问题九讲笔记_01背包
  12. 程序员宝典 c语言版,C语言宝典app下载
  13. 一文搞懂Handler机制原理
  14. 代码注释的艺术,优秀代码真的不需要注释吗?
  15. 一些相似单词的区别之处
  16. 暑假2019培训:Day3Day4提高组测试赛
  17. WPF入门教程系列(2)---基础篇
  18. Windows应用程序C#创建MDI父窗体和子窗体
  19. 有占空比的c语言中断程序,如何用51程序改变占空比
  20. 计算机教育中缺失的一课,劝学弟学姝们一句,一定要趁早补上,工作后会事半功倍

热门文章

  1. MediaPlayer 播放视频的方法
  2. 工单更改历史记录(轉載)
  3. Unable to open /dev/sda的原因之一
  4. C++ _countf
  5. Sql 实现自动添加行数标记
  6. Java sdk及tomcat安装设置
  7. 把一个数据库的数据插入到另外一个数据库
  8. Linux驱动开发中与设备树相关的6种debug方法
  9. Android 亮屏速度分析
  10. linux inputuevent使用