C#对象的三种序列化

要让一个对象支持.Net序列化服务,用户必须为每一个关联的类加上[Serializable]特性。如果类中有些成员不适合参与序列化(比如:密码字段),可以在这些域前加上[NonSerialized]特性。

  C#支持三种序列化格式:二进制格式(使用BinaryFormatter序列化器)、SOAP格式(使用SoapFormatter序列化器)、XML格式(使用XmlSerializer序列化器)。这三种序列化器的区别如下:

  二进制格式可序列化一个类型的所有可序列化字段,不管它是公共字段还是私有字段。SOAP格式和XML格式仅能序列化公共字段或拥有公共属性的私有字段,未通过属性公开的私有字段将被忽略。

  使用二进制格式序列化时,它不仅是将对象的字段数据进行持久化,也持久化每个类型的完全限定名称和定义程序集的完整名称(包括包称、版本、公钥标记、区域性),这些数据使得在进行二进制格式反序列化时亦会进行类型检查。SOAP格式序列化通过使用XML命名空间来持久化原始程序集信息。而XML格式序列化不会保存完整的类型名称或程序集信息。这便利XML数据表现形式更有终端开放性。如果希望尽可能延伸持久化对象图的使用范围时,SOAP格式和XML格式是理想选择。

  BinaryFormatter和SoapFormatter类型通过实现IFormatter和IRemotingFormatter接口实现序列化。

  IFormatter接口定义了核心的Serialize和Deserialize方法用于序列化和反序列化。

  IRemotingFormatter接口重载了Serialize和Deserialize方法,使风格更适合分布式持久化。

  示例代码:

using System;
using System.Collections.Generic;
using System.Text;
using System.Runtime.Serialization.Formatters.Binary;
using System.Runtime.Serialization.Formatters.Soap;
using System.IO;
using System.Xml.Serialization;

namespace CollectionSerialize
{
class Program
{
static void Main( string [] args)
{
// 文件名称
string fileName = " Programmers.dat " ;

// 创建Programmer列表,并添加对象
List < Programmer > list = new List < Programmer > ();
list.Add(
new Programmer( " Coder1 " , false , " C " ));
list.Add(
new Programmer( " Coder2 " , false , " C++ " ));
list.Add(
new Programmer( " Coder3 " , false , " Java " ));

// 创建文件流
Stream fStream = null ;
fStream
= FileReset(fStream, fileName);

// 使用二进制序列化器
BinaryFormatter binFormat = new BinaryFormatter();
// 将list序列化到文件中
binFormat.Serialize(fStream, list);
// 清空列表
list.Clear();
// 重置流位置
fStream.Position = 0 ;
// 反序列化,注意要将结果转型
list = (List < Programmer > )binFormat.Deserialize(fStream);

// 输出
Print(list);
fStream
= FileReset(fStream, fileName);

// 使用XML序列化
// 注意使用此构造器时必须在第一个参数传入序列化的类型,第二个参数传入序列化所涉及的相关类型
XmlSerializer xmlFormat =
new XmlSerializer( typeof (List < Programmer > ),
new Type[] { typeof (Programmer), typeof (Person) });
// 反序列化
xmlFormat.Serialize(fStream, list);
list.Clear();
fStream.Position
= 0 ;
// 反序列化,注意要将结果转型
list = (List < Programmer > )xmlFormat.Deserialize(fStream);

Print(list);
fStream
= FileReset(fStream, fileName);

// 使用SOAP序列化
SoapFormatter soapFormat = new SoapFormatter();
// 序列化,Soap不能序列化泛型对象,所以只能指定序列化一个Programmer对象
soapFormat.Serialize(fStream, list[ 0 ]);
list.Clear();
fStream.Position
= 0 ;
// 反序列化
list.Add((Programmer)soapFormat.Deserialize(fStream));

Print(list);
fStream.Close();

Console.ReadKey();
}

// 输出程序员列表
static void Print(List < Programmer > list)
{
Console.WriteLine(
" 程序员信息列表: " );
foreach (Programmer p in list)
{
Console.WriteLine(
" 姓名:{0} 性别:{1} 编程语言:{2} " ,
p.Name, p.Sex.ToString(), p.Language);
}
}

// 重置文件
static FileStream FileReset(Stream fStream, string fileName)
{
// 关闭文件流
if (fStream != null )
{
fStream.Close();
}

// 删除文件
File.Delete(fileName);
// 新建文件流
return new FileStream(fileName, FileMode.OpenOrCreate,
FileAccess.ReadWrite, FileShare.None);
}
}

[Serializable]
// 必须添加序列化特性
public class Person
{
// 姓名
public string Name;
// 性别
public bool Sex;

// 必须提供无参构造器,否则XmlSerializer将出错
public Person() { }

// 构造函数
public Person( string name, bool sex)
{
this .Name = name;
this .Sex = sex;
}
}

[Serializable]
// 必须添加序列化特性
public class Programmer : Person
{
// 编程语言
public string Language;

// 必须提供无参构造器,否则XmlSerializer将出错
public Programmer() { }

// 构造函数
public Programmer( string name, bool sex, string language)
:
base (name, sex)
{
this .Language = language;
}
}
}

  程序运行结果如下:

  需要注意的是:

  1. SoapFormatter不能序列化泛型对象。

  2. XmlSerializer的构造器需要传入序列化涉及的相关类型信息。

出处:http://www.csharpwin.com/dotnetspace/12740r6571.shtml

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值