介绍
  序列化是将对象状态转换为可保持或传输的形式的过程。序列化的补集是反序列化,后者将流转换为对象。这两个过程一起保证数据易于存储和传输。
  .NET Framework 提供了两个序列化技术:
  二进制序列化保持类型保真,这对于多次调用应用程序时保持对象状态非常有用。例如,通过将对象序列化到剪贴板,可在不同的应用程序之间共享对象。您可以将对象序列化到流、磁盘、内存和网络等。远程处理使用序列化,“按值”在计算机或应用程序域之间传递对象。
  XML 序列化只序列化公共属性和字段,并且不保持类型保真。当您希望提供或使用数据而不限制使用该数据的应用程序时,这一点非常有用。由于 XML 是开放式的标准,因此它对于通过 Web 共享数据来说是一个理想选择。SOAP 同样是开放式的标准,这使它也成为一个理想选择。
  详细
  具体命名空间:
  System.Runtime.Serialization
  包含可用于序列化和反序列化对象的类。(包括System.Runtime.Serialization.Formatters.Binary.BinaryFormatter,还有WCF中用到的DataContractAttribute, DataMemberAttribute)
  System.Xml.Serialization
  包含可用于将对象序列化为 XML 格式的文档或流的类。
  WCF大家很熟悉,一般的书籍都对基础的东西有很多内容的讲解,这里就对非WCF的一些序列化技巧抛个砖。
  一:序列化标记
  需要序列化:[Serializable]也可以写成[SerializableAttribute]
  特性“Serializable”只在“class, struct, enum, delegate”声明中有效。所以只能在类,结构体等上面标记。
  不需要序列化:[NonSerialized]也可以写成[NonSerializedAttribute]
  特性“NonSerialized”只在“field”声明中有效。所以只能在字段上标记,连属性器都不行。
  二:特殊情况:
  事件的标记:
  [field: NonSerializedAttribute()],需要加入field标记。
  属性的标记:
  其实我们叫的属性是属性器,是一对Get,Set方法。既然是方法,当然不是字段了,所以是不能序列化标记或者排除的,那我们怎么去处理某些属性不需要序列化的情况列。方法也是有的,需要把属性器中的Get,Set方法写实,即该有的字段还是得定义,不能偷懒,然后在该有的字段上面标记为不需要序列化。
  三:序列化的特殊用法
  学过C#的时候,大家都知道了个值类型,引用类型的概念,也可能知道了ICloneable这个接口,这个克隆接口可以复制对象,如实例化个student,然后调用Clone()即可以得到该对线的浅层副本。
  浅层克隆就是只把改对象的值类型和引用类型的地址复制了,但是,原来对象中的被引用类型的对象发生改变,比如:student类中有个classroom,classroom中的某个字段发生改变,这样克隆后的对线的classroom的值也是会变的。除非classroom这个类也实现ICloneable接口。
  序列化克隆的好处就是不用考虑浅层复制,深层复制,直接将要克隆的对象序列化,然后反序列化得到的对象就是我们期望的结果。
 处理
  按照上面的说明,代码如下:
  Student类
  1 [Serializable]
  2 public class Student
  3 {
  4 [field: NonSerializedAttribute()]
  5 public event EventHandler Changed;
  6 [NonSerialized]
  7 private ExParam param;
  8
  9 public string ID
  10 {
  11 get;
  12 set;
  13 }
  14
  15 public string Name
  16 {
  17 get;
  18 set;
  19 }
  20
  21 public ClassRoom Room
  22 {
  23 get;
  24 set;
  25 }
  26
  27 public ExParam Param
  28 {
  29 get
  30 {
  31 return param;
  32 }
  33 set
  34 {
  35 param = value;
  36 }
  37 }
  38 }
  ClassRoom类
  1 [Serializable]
  2 public class ClassRoom
  3 {
  4
  5 public string Name
  6 {
  7 get;
  8 set;
  9 }
  10
  11 public string Address
  12 {
  13 get;
  14 set;
  15 }
  16 }
  ExParam类
  1 public class ExParam
  2 {
  3 public string Name
  4 {
  5 get;
  6 set;
  7 }
  8 }
  Util类
  1 public class Util
  2 {
  3 public static byte[] SerializeObject(object obj)
  4 {
  5 if (obj == null)
  6 return null;
  7
  8 using (MemoryStream memory = new MemoryStream())
  9 {
  10 BinaryFormatter formatter = new BinaryFormatter();
  11 formatter.Serialize(memory, obj);
  12 memory.Position = 0;
  13 byte[] read = new byte[memory.Length];
  14 memory.Read(read, 0, read.Length);
  15 memory.Close();
  16 return read;
  17 }
  18 }
  19
  20
  21 public static object DeserializeObject(byte[] data)
  22 {
  23 object obj = null;
  24 if (data == null)
  25 return obj;
  26
  27 using (MemoryStream memory = new MemoryStream(data))
  28 {
  29 memory.Position = 0;
  30 BinaryFormatter formatter = new BinaryFormatter();
  31 obj = formatter.Deserialize(memory);
  32 memory.Close();
  33 return obj;
  34 }
  35 }
  36 }
  主窗体
  1 private void Form1_Load(object sender, EventArgs e)
  2 {
  3 Student student = new Student()
  4 {
  5 ID = "201401",
  6 Name = "攻城狮",
  7 Room = new ClassRoom()
  8 {
  9 Name = "博客园",
  10 Address = "小山村"
  11 },
  12 Param = new ExParam()
  13 {
  14 Name = "程序猿"
  15 }
  16 };
  17
  18 byte[] data = Util.SerializeObject(student);
  19
  20 Student student1 = Util.DeserializeObject(data) as Student;
  21
  22 Print(student);
  23 Print(student1);
  24 }
  25
  26 private void Print(Student student)
  27 {
  28 string info =string.Format("{0}{1}{2}{3}"
  29 , "hashcode:" + student.GetHashCode().ToString() + " "
  30 , student.ID + " " + student.Name + " "
  31 , student.Room != null ? student.Room.Name + " " + student.Room.Address + " "+student.Room.GetHashCode().ToString()+" " : "room is null "
  32 , student.Param != null ? student.Param.Name : "param is null"
  33 );
  34 listPrint.Items.Add(info);
  35 }
  从上述代码输出的结果我们可以看出
  student是被序列化的,student1是用student的序列化的二进制反序列化出来的,两个的hashcode不一样,所以是两个对象。
  标记了序列化的字段都被序列化了,没标记的序列化字段Param是空的托福答案
  student中的属性Room是引用类型,标记为序列化,student和student1的Room里的值内容一样但是hashcode不一样,所以这Room也是我们期望的两个对象。

.NET序列化的一点技巧的更多相关文章

  1. .NET序列化的一点技巧(附Demo)

    阅读目录 介绍 详细 处理 结论 Demo下载 介绍 序列化是将对象状态转换为可保持或传输的形式的过程.序列化的补集是反序列化,后者将流转换为对象.这两个过程一起保证数据易于存储和传输. .NET F ...

  2. dubbo序列化的一点注意

    最近工作中遇见了一个小问题,在此记录一下,大致是这样的,有一父类,有一个属性traceId,主要是记录日志号,这样可以把所有日志串起来,利于排查问题,所有的pojo对象继承于此,但是其中一同事在子类p ...

  3. Javascript 性能优化的一点技巧

    把优秀的编程方式当成一种习惯,融入到日常的编程当中.下图是今天想到的一点Javascript 性能优化的技巧,分享一下,抛砖引玉.

  4. Json.Net组件指定/忽略序列化字段属性技巧知识点

    我们在用Json.Net序列化组件序列化类的时候,经常有这样的一个需求:指定被序列化类中的某些字段属性是要忽略的,或者是指定字段属性序列化 比如下面这个类: public class Bar { pu ...

  5. C语言下for循环的一点技巧总结

    for循环是普遍应用与各种计算机语言的一种循环方式. 一般情况下, for循环规则:for(条件一:条件二:条件三) 条件一为满足条件,也就是条件一为1时,进入这个for循环.条件二为循环条件,也就是 ...

  6. SpringMVC DispatcherServlet在配置Rest url-pattern的一点技巧

    SpringMVC的Controller中已经有了@RequestMapping(value = "detail.do", method = RequestMethod.GET)的 ...

  7. 关于反编译pyc的一点技巧

    现在最流行的是用 https://github.com/rocky/python-uncompyle6 但是有些python小版本不一样,比如2.7.6的某版本,开头的magic number在这个项 ...

  8. java.io.Serializable 序列化接口

    什么是序列化.反序列化? Serialization(序列化)是一种将对象以一连串的字节描述的过程: 反序列化deserialization是一种将这些字节重建成一个对象的过程. 序列化通俗一点说就是 ...

  9. 透过byte数组简单分析Java序列化、Kryo、ProtoBuf序列化

    序列化在高性能网络编程.分布式系统开发中是举足轻重的之前有用过Java序列化.ProtocolBuffer等,在这篇文章这里中简单分析序列化后的byte数组观察各种序列化的差异与性能,这里主要分析Ja ...

随机推荐

  1. 大众点评网王宏:从.Net迁移向Java平台 - 51CTO.COM

    大众点评网王宏:从.Net迁移向Java平台 - 51CTO.COM 大众点评网王宏:从.Net迁移向Java平台

  2. 通过例子学python(1)

    第一章 基础知识 1.4 数字和表达式 # -*- coding: cp936 -*- # 1.4 数字和表达式 # ** 表示幂(乘方)运算 #1.4.1 长整型数 print(9999999999 ...

  3. Musical Theme - poj 1743(求最大不重叠重复子串)

    题目大意: * 有N(1 <= N <=20000)个音符的序列来表示一首乐曲,每个音符都是1..88范围内的整数,现在要找一个重复的主题. * “主题”是整个音符序列的一个子串,它需要满 ...

  4. 从奥鹏一个答案提取页面 看jquery知识点

     http://oldlearn.open.com.cn/OEMSExercise/HomeworkReview.aspx?HomeworkId=9c034488-0a3d-4b9d-a6cc-e42 ...

  5. Git服务器仓库的搭建和客户端使用方法

    环境说明: 1.fedora21  桌面系统  2.已经配置好yum仓库 一.安装git # yum install git 1.1 创建git用户 创建git账户并登录,直接指定用户目录到/home ...

  6. UVA - 10785 The Mad Numerologist

    题目链接 这个题又犯了省题不清的错误.导致不停 wa.唉. 题目意思是给你一个长度L,然后和一张表相应每一个大写字母的value值.你须要依照一定规则找出长度为L的序列. 注意  序列的value值要 ...

  7. Qt解析XML文件(QXmlStreamReader)

    (2013-08-03 10:53:53) 转载▼       如何使用QXmlStreamReader来解析格式良好的XML,Qt的文档中指出,它是一种更快.更方便的Qt自己的SAX解析器(QXml ...

  8. Note | Javascript权威指南[第六版] 第1章:Javascript概述

       JavaScript是一门高端的.动态的.弱类型的编程语言,非常适合面向对象和函数式的编程风格.JavaScript的语法源自Java,它的一等函数(first-class function)来 ...

  9. ios从相册:摄像头中获取视频

    ios从相册/摄像头中获取视频 如何从相册中获取视频 使用的是一个和获取照片相同的类UIImagePickerController //相册中获取视频 - (IBAction)clickViedoOF ...

  10. U盘安装centos 6.4教程(总算是弄好了

    参考:http://blog.chinaunix.net/uid-27666459-id-3342477.html http://www.linuxidc.com/Linux/2011-05/3569 ...