zoukankan      html  css  js  c++  java
  • 第24章 运行时序列化

    什么是序列化和反序列化

    序列化(serialization)是将一个对象或者对象图(对象在特定的时间点的一个视图)转换成一个字节流的过程。反序列化(deserialization)是将一个字节流转换回对象图的过程。

    应用场景:

    • 应用程序的状态(对象图)可以保存到磁盘文件或数据库中,并在应用程序下次运行时恢复。
    • 一组对象可以轻松复制到Windows 窗体的剪贴板中,再粘贴回同一个或者另一个应用程序。
    • 将对象按值从一个应用程序域中发送到另一个程序域

    24.1 序列化/反序列化快速入门

    http://blog.csdn.net/gavinchengshubo/article/details/8378441

    引用 System.Runtime.Serialization.Formatters.Binary

    复制代码
    private static MemoryStream SerializeToMemory(object objectGraph) {
        MemoryStream stream = new MemoryStream();
        BinaryFormatter formatter = new BinaryFormatter();
        formatter.Serialize(stream, objectGraph);
        return stream;
    }
    private static Object DeserializeFormMemory(Stream stream) {
        BinaryFormatter formatter = new BinaryFormatter();
        return formatter.Deserialize(stream);
    }
    static void Main(string[] args)
    {
        List<string> objectGraph = new List<string> {"hzd","ian.w","whx1973" };
        Stream stream = SerializeToMemory(objectGraph);
        stream.Position = 0;
        objectGraph = null;
        objectGraph = (List<string>)DeserializeFormMemory(stream);
        foreach (var s in objectGraph)
        {
            Console.WriteLine(s);
        }
    }
    复制代码
    SerializeToMemory方法创建MemoryStream对象,用来做序列化完成后字节存在的容器,创建BinaryFormatter对象formatter(格式化器),调用Serialize方法,传递一个流对象的引用和要被序列化
    的对象的引用。流对象可以是任何一个从System.IO.Stream抽象基类派生的任何类型的一个对象 (MemoryStream,FileStream,NetworkSteam),第二个参数可以是任何东西,如Int32 、String、
    List<String>等等
    DeserializeFormMemory 方法创建 BinaryFormatter 对象 formatter,调用 Deserialize 方法,此方法获取流作为参数,返回对反序列化的对象图中的根对象的一个引用。在内部,格式化器的
    Deserialize方法会检查流的内容,够造流中的所有对象的实例,并初始化所有这些对象的字段,使它们具有与当初序列化时相同的值。通常要将Deserialize方法返回的对象引用转型为应用程序期待的类型。

    使类型可序列化
    类型默认是不可以序列化的,需要定制System.SerializableAttributeattribute(此attributeSystem命名空间定义的),SerializableAttribute这个定制attribute只能应用于引用
    类型(class)、值类型(struct)、枚举类型(enum)和委托类型(delegate)。此外SerializableAttribute attribute不会被派生类继承
    控制序列化和反序列化
    SerializableAttribute 这个定制的attribute应用于一个类型时,所有的实例字段(public private protected 等)都会被序列化。使用System.NonSerializedAttribute 定制attribute
    来指明类型的哪些字段不应序列化。此attribute同样位于System命名空间
    复制代码
    [Serializable]
    internal class Circle
    {
        private double m_radius;
        [NonSerialized]
        private Double m_area;
    
        public Circle(double radius)
        {
            m_radius = radius;
            m_area = Math.PI * m_radius * m_radius;
        }
    }
    复制代码
    上述代码中,Circle的对象可以序列化 ,然而反序列化时,Circle对象的 m_area 字段会被设置为 0 ,不能得到正确的结果,修改上面的代码为 
    复制代码
    [Serializable]
    internal class Circle
    {
        private double m_radius;
        [NonSerialized]
        private Double m_area;
    
        public Circle(double radius)
        {
            m_radius = radius;
            m_area = Math.PI * m_radius * m_radius;
        }
        [OnDeserialized]
        private void OnDeserialized(StreamingContext context)
        {
            m_area = Math.PI * m_radius * m_radius;
        }
    }
    复制代码

    在修改的代码中 ,包含了一个用 System.Runtime.Serialization.OnDeserializedAttribute定制的 特性 进行了标记的方法 ,每次反序列化类型的一个实例 ,格式化器都会检查类型中是否定义了一个应用该特性的方法 。除了 OnDeserializedAttribute这个定制的特性 ,System.Runtime.Serialization命名空间还包含 OnDeserializingAttribute,OnSerializingAttribute,OnSerializedAttribute这些定制的attribute。

  • 相关阅读:
    Codeforces Round #436 C. Bus
    Codeforces Round #436 B. Polycarp and Letters
    Codeforces Round #436 A. Fair Game
    Codeforces Round #439 C. The Intriguing Obsession
    Codeforces Round #438 C. Qualification Rounds
    Codeforces Round #438 B. Race Against Time
    hdu 1394 Minimum Inversion Number (树状数组求逆序对)
    hdu 6318 Swaps and Inversions (线段树求逆序对数)
    ACM/ICPC 2018亚洲区预选赛北京赛站网络赛 D 80 Days (线段树查询最小值)
    hdu 6299 Balanced Sequence (贪心)
  • 原文地址:https://www.cnblogs.com/chrisghb8812/p/5618251.html
Copyright © 2011-2022 走看看