zoukankan      html  css  js  c++  java
  • 为什么实现Serializbale接口就能够进行序列化?

    从所周知,Serializbale接口是个空的接口,并没有定义任何方法。那么问题来了,为什么需要序列化的接口只要实现Serializbale接口就能够进行序列化?

    这要从序列化过程的源码说起。举个例子这里有个可序列化的Parent类,然后我们用一个TestSeri类对其序列化。

    public class Parent implements Serializable {
    
        private static final long serialVersionUID = 1234L;
        
        public Parent1(String name,int age){
            this.name = name;
            this.age = age;
        }
        
        private String name;
        private int age;
    
        
        public String toString(){
            return "Parent:"+name+" "+age;
        }
        
    }
    public class TestSeri {
        
        public static  void seri(Parent parent){
            try {
                FileOutputStream fo = new FileOutputStream("src/est.txt");
                ObjectOutputStream oos = new ObjectOutputStream(fo);
                oos.writeObject(parent);
                oos.flush();
                oos.close();
            } catch (Exception e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }        
        }
        
        public static void main(String[] args){
            Parent parent = new Parent("ouym",24);
            seri(parent);
                    
        }

    序列话的过程主要有三步:

    (1)新建文件输出流用来指定一个位置存储序列化的内容。

    (2)新建一个ObjectOutputStream对象oos

    (3)序列化:调用writeObject(parent)方法。

    关键看第三部writeObject的内部实现过程:

    public final void writeObject(Object obj) throws IOException {
        //省略部分代码
        try {
            // 调用writeObject0()方法序列化
            writeObject0(obj, false);
        } catch (IOException ex) {
            if (depth == 0) {
                writeFatalException(ex);
            }
            throw ex;
        }
    }

    可见writeObject方法的主要实现过程交给了writeObject0(obj,false)方法。

     1 private void writeObject0(Object obj, boolean unshared)
     2     throws IOException
     3 {
     4     // 一些省略代码
     5     try {
     6         // 一些省略代码,其他的细节我们不深入
     7         // remaining cases
     8         if (obj instanceof String) {
     9             writeString((String) obj, unshared);
    10         } else if (cl.isArray()) {
    11             writeArray(obj, desc, unshared);
    12         } else if (obj instanceof Enum) {
    13             writeEnum((Enum) obj, desc, unshared);
    14         } else if (obj instanceof Serializable) {
    15             // 被序列化对象实现了Serializable接口
    16             writeOrdinaryObject(obj, desc, unshared);
    17         } else {
    18             if (extendedDebugInfo) {
    19                 throw new NotSerializableException(
    20                     cl.getName() + "
    " + debugInfoStack.toString());
    21             } else {
    22                 throw new NotSerializableException(cl.getName());
    23             }
    24         }
    25     } finally {
    26         depth--;
    27         bout.setBlockDataMode(oldMode);
    28     }
    29 }

    从上述代码第8行开始,我们知道String,数组和枚举类型可以直接序列化(不难猜出String和Enum类实现了Serializbale接口)。若不是上述三种类型的话,接下来重点看14到16行代码,如果对象实现了Serializbale接口的话,就用writeOrdinaryObject()方法进行序列化操作。这里我们就不看writeOrdinaryObject方法的细节了,因为我们已经找到了标题的答案。Serializable接口这是一个标识,告诉程序所有实现了他的对象都可以进行序列化。

    更多关于序列化的详情推荐大神博客:http://www.importnew.com/24490.html

  • 相关阅读:
    双主MySQL+keepalived高可用配置
    centos6.8服务器部署svn
    Centos6下rpm安装MySQL5.6
    CentOS6.8下部署Zabbix3.0
    python核心编程第六章练习6-15
    python核心编程第六章练习6-14
    scp 将数据从一台linux服务器复制到另一台linux服务器
    $config['base_url'] BASE_URL
    ubunt设置终端快捷键设置 及 常用快捷键
    URL 路由
  • 原文地址:https://www.cnblogs.com/ouym/p/8795885.html
Copyright © 2011-2022 走看看