• 我对序列化(Serializable)的理解


    转自:http://blog.tianya.cn/blogger/post_show.asp?BlogID=764&PostID=3231409

    序列化是把一个对象的状态写入一个字节流的过程。
      对象是类的一个实例,系统在使用对象的过程是先加载类,创建类的一个实例即对象,然后初始化,最后就可以使用对象的属性和方法了,所有的这一切都是在内存中进行的,也就是说,每次使用对象都是重新创建。
      序列化把一个对象的状态写入一个字节流,就可以把对象存储在磁盘上了。:)
      那么序列化到底有什么用处呢,先看看别人的文章。
         
    #日志日期:2005-11-17 星期四(Thursday) 晴
    评论人:7phoenix 评论日期:2005-11-17 9:22
      serialization有什么用?
        
      Object serialization 允许你将实现了Serializable接口的对象转换为字节序列,这些字节序列可以被完全存储以备以后重新生成原来的对象。 
        
      serialization不但可以在本机做,而且可以经由网络操作(就是猫小说的RMI)。这个好处是很大的----因为它自动屏蔽了操作系统的差异,字节顺序等。比如,在Window平台生成一个对象并序列化之,然后通过网络传到一台Unix机器上,然后可以在这台Unix机器上正确地重构这个对象。 
      Object serialization主要用来支持2种主要的特性: 
      1。Java的RMI(remote method invocation).RMI允许象在本机上一样操作远程机器上的对象。当发送消息给远程对象时,就需要用到serializaiton机制来发送参数和接收返回直。 
        
      2。Java的JavaBeans. Bean的状态信息通常是在设计时配置的。Bean的状态信息必须被存起来,以便当程序运行时能恢复这些状态信息。这也需要serializaiton机制。
      

    评论人:7phoenix 评论日期:2005-11-17 9:22
      接下来,看一个例子
      
      Serializable接口实例
      
      "序列化是把一个对象的状态写入一个字节流的过程,它执行RMI,RMI允许一台机器上的JAVA对象调用不同机器上的JAVA对象方法,对象可以作为参数提供给那个远程方法,发送机序列化该对象并传送它,接收机执行反序列化。序列化和反序列化的关系图表可形成包含循环引用的顺序图表。这是整个序列化的总体思想。 而Serializable接口属于支持序列化的一个接口,只有一个实现它的对象可以被序列化工具存储和回复,Serializable接口没有定义任何成员,只用来表示一个类可以被序列化,若该类可以序列化,那么它的所有子类都可以。"
      
      
      /*
       * Created on 2005-3-30
       *
       * TODO To change the template for this generated file go to
       * Window - Preferences - Java - Code Style - Code Templates
       */
      
      package com.tiantian;
      
      import java.io.*;
      
      /**
       * @author Administrator
       * 
       * TODO To change the template for this generated type comment go to Window -
       * Preferences - Java - Code Style - Code Templates
       */
      public class BugReport implements Serializable { //implement Serializable
       private Float m_SoftwareVersion; //version of software
      
       private String m_ErrorDescription; //error code
      
       private int m_Severity;
      
       public BugReport(Float SoftwareVersion, String ErrorDescription,int Severity) {
       m_SoftwareVersion = SoftwareVersion;
       m_ErrorDescription = ErrorDescription;
       m_Severity = Severity;
       }
      
       public BugReport() {
       } // for reconstituting serialized objects
      
       public void save(OutputStream os) throws IOException {
       //this is a function for serializing a object to a stream
       try {
       ObjectOutputStream o = new ObjectOutputStream(os);
       o.writeObject(this);
       o.flush();
       } catch (IOException e) {
       throw e;
       }
       }
      
       public BugReport restore(InputStream is) throws 
       IOException,ClassNotFoundException {
       //this is function for restoring a object from a stream
       BugReport RestoredBugReport = null;
       try {
       ObjectInputStream o = new ObjectInputStream(is);
       RestoredBugReport = (BugReport) o.readObject();
       } catch (IOException e) {
       throw e;
       } catch (ClassNotFoundException e) {
       throw e;
       }
       return RestoredBugReport;
       }
      
       public static void main(String[] args) {
       //this is demo for SERIALIZABLE
       System.out.println("success");
       BugReport bug = new BugReport(new Float(1.0),
       "Crashes when spell checker nvoked", 
       2);
       //System.out.println(bug.toString());
       try {
       FileOutputStream os = new FileOutputStream("MyBug.test");
       bug.save(os);
       } catch (FileNotFoundException e) {
       // TODO Auto-generated catch block
       e.printStackTrace();
       } catch (IOException e) {
       // TODO Auto-generated catch block
       e.printStackTrace();
       }
      
       }
      }

    评论人:7phoenix 评论日期:2005-11-17 9:23
        最后比较一下实现序列化的两种方法
        比较java.io.Externalizable和java.io.Serializable 
         
        即使你没有用过对象序列化(serialization),你可能也知道它。但你是否知道 Java 还支持另外一种形式的对象持久化,外部化(externalization)?
        
        下面是序列化和外部化在代码级的关联方式:
        
        public interface Serializable {} 
        
        public interface Externalizable extends Serializable {
         void readExternal(ObjectInput in);
         void writeExternal(ObjectOutput out);
        } 
        
        序列化和外部化的主要区别
        
        外部化和序列化是实现同一目标的两种不同方法。下面让我们分析一下序列化和外部化之间的主要区别。
        
        通过Serializable接口对对象序列化的支持是内建于核心 API 的,但是java.io.Externalizable的所有实现者必须提供读取和写出的实现。Java 已经具有了对序列化的内建支持,也就是说只要制作自己的类java.io.Serializable,Java 就会试图存储和重组你的对象。如果使用外部化,你就可以选择完全由自己完成读取和写出的工作,Java 对外部化所提供的唯一支持是接口:
        
        voidreadExternal(ObjectInput in)
        void writeExternal(ObjectOutput out) 
        
        现在如何实现readExternal() 和writeExternal() 就完全看你自己了。
        
        序列化会自动存储必要的信息,用以反序列化被存储的实例,而外部化则只保存被存储的类的标识。当你通过java.io.Serializable接口序列化一个对象时,有关类的信息,比如它的属性和这些属性的类型,都与实例数据一起被存储起来。在选择走Externalizable这条路时,Java 只存储有关每个被存储类型的非常少的信息。
        
        每个接口的优点和缺点
        
        Serializable接口
        
        · 优点:内建支持
        
        · 优点:易于实现
        
        · 缺点:占用空间过大
        
        · 缺点:由于额外的开销导致速度变比较慢
        
        Externalizable接口
        
        · 优点:开销较少(程序员决定存储什么)
        
        · 优点:可能的速度提升
        
        · 缺点:虚拟机不提供任何帮助,也就是说所有的工作都落到了开发人员的肩上。
        
        在两者之间如何选择要根据应用程序的需求来定。Serializable通常是最简单的解决方案,但是它可能会导致出现不可接受的性能问题或空间问题;在出现这些问题的情况下,Externalizable可能是一条可行之路。
        
        要记住一点,如果一个类是可外部化的(Externalizable),那么Externalizable方法将被用于序列化类的实例,即使这个类型提供了Serializable方法:
        
        private void writeObject()
        private void readObject() 
  • 相关阅读:
    01-Git 及其可视化工具TortoiseGit 的安装和使用
    IntelliJ IDEA中Warning:java:源值1.5已过时, 将在未来所有发行版中删除
    JVM学习笔记四_垃圾收集器与内存分配策略
    JVM学习笔记三_异常初步
    CentOs7 图形界面和命令行界面切换
    基本概念一
    JVM学习笔记二_对象的创建、布局和定位
    JVM学习笔记一_运行时数据区域
    个人阅读作业二
    软件工程随笔
  • 原文地址:https://www.cnblogs.com/x_wukong/p/3420775.html
Copyright © 2020-2023  润新知