这一篇主要是用来介绍关于C#中的XML序列化的问题,这个相信大家一定会经常使用它,特别是在WPF中,有时候我们需要将我们后台的数据保存在数据库中,从而在软件下一次启动的时候能够自动去加载这些数据,由于我们的这些Model中字段众多,如果单独进行保存那是不太现实的,这个时候将这些字段序列化成xml字符串并保存在数据库中就是一个不错的选择,当我们需要这些数据的时候我们也可以反过来将其序列化为一些字段,最终达到我们的效果,首先我们来看看是如何实现的?
public class XMLUtil { /// <summary> /// XML & Datacontract Serialize & Deserialize Helper /// </summary> /// <typeparam name="T"></typeparam> /// <param name="serialObject"></param> /// <returns></returns> public static string Serializer<T>(T serialObject) where T : class { try { XmlSerializer ser = new XmlSerializer(typeof(T)); System.IO.MemoryStream mem = new MemoryStream(); XmlTextWriter writer = new XmlTextWriter(mem, Encoding.UTF8); ser.Serialize(writer, serialObject); writer.Close(); return Encoding.UTF8.GetString(mem.ToArray()); } catch (Exception ex) { return null; } } public static T Deserialize<T>(string str) where T : class { try { XmlSerializer mySerializer = new XmlSerializer(typeof(T)); StreamReader mem2 = new StreamReader( new MemoryStream(System.Text.Encoding.UTF8.GetBytes(str)), System.Text.Encoding.UTF8); return (T)mySerializer.Deserialize(mem2); } catch (Exception) { return null; } } }
微软为我们提供的XmlSerializer这个类就为我们提供了这个可能,在序列化的过程中我们需要注意下面的情况,所有的属性必须是可序列化的对象,像BitmapImage、SolidColorBrush等这些对象都是不能够进行序列化的对象,如果用上面的方法进行序列化时将返回null,正确的方式是在这些字段上面加上[XmlIgnore]说明,从而在进行序列化时候跳过这些对象,就像下面的方式。
/// <summary> ///背景颜色 /// </summary> private SolidColorBrush _BackgroundColor; [XmlIgnore] public SolidColorBrush BackgroundColor { get { return _BackgroundColor; } set { if (value != _BackgroundColor) { _BackgroundColor = value; OnPropertyChanged("BackgroundColor"); } } }
那么像上面的这个SolidColorBrush对象该怎样去进行序列化呢,这里我们选择将当前颜色的ARGB值保存在一个byte数组中,从而在反序列化的时候通过Color.FromArgb的方式进行还原,就像下面的方式。
byte[] colorByte=savedModel.ConfigurationBaseModel.BackgroundColorArgb; Color backColor=Color.FromArgb(colorByte[0],colorByte[1],colorByte[2],colorByte[3]); sourceBaseModel.BackgroundColor = new SolidColorBrush(backColor);
那么这个对象在进行序列化的时候该怎么进行保存呢?同样的原理我们可以通过下面的方式。
/// <summary> ///背景颜色 /// </summary> private SolidColorBrush _BackgroundColor; [XmlIgnore] public SolidColorBrush BackgroundColor { get { return _BackgroundColor; } set { if (value != _BackgroundColor) { _BackgroundColor = value; OnPropertyChanged("BackgroundColor"); } } } /// <summary> ///背景颜色ARGB /// </summary> private byte[] _BackgroundColorArgb=new byte[4]; [XmlArray("argb"),XmlArrayItem("value")] public byte[] BackgroundColorArgb { get { if (null != _BackgroundColor) { Color color = _BackgroundColor.Color; _BackgroundColorArgb[0] = color.A; _BackgroundColorArgb[1] = color.R; _BackgroundColorArgb[2] = color.G; _BackgroundColorArgb[3] = color.B; } return _BackgroundColorArgb; } set { if (value != _BackgroundColorArgb) { _BackgroundColorArgb = value; OnPropertyChanged("BackgroundColorArgb"); } } }
这里在实际的使用中发现,就像byte数组必须通过[XmlArray("argb"),XmlArrayItem("value")] 这类型的标识来将其分类,在将其序列化完毕以后,我们可以看看这个BackgroundColorArgb字段最终是通过怎样的方式来保存的?
在进行反序列化的时候会将这个argb和value反序列化为一个byte数组。
除了这些特例意外,有时候经常需要将一些对象的数组进行序列化,那么原理是什么呢?这里我借用别人的一个例子来进行相关的说明。
数组的Xml序列化需要使用XmlArrayAttribute和XmlArrayItemAttribute;XmlArrayAttribute指定数组元素的Xml节点名,XmlArrayItemAttribute指定数组元素的Xml节点名。
如下代码示例:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Xml.Serialization; namespace UseXmlSerialization { class Program { static void Main(string[] args) { //声明一个猫咪对象 var cWhite = new Cat { Color = "White", Speed = 10, Saying = "White or black, so long as the cat can catch mice, it is a good cat" }; var cBlack = new Cat { Color = "Black", Speed = 10, Saying = "White or black, so long as the cat can catch mice, it is a good cat" }; CatCollection cc = new CatCollection { Cats = new Cat[] { cWhite,cBlack} }; //序列化这个对象 XmlSerializer serializer = new XmlSerializer(typeof(CatCollection)); //将对象序列化输出到控制台 serializer.Serialize(Console.Out, cc); Console.Read(); } } [XmlRoot("cats")] public class CatCollection { [XmlArray("items"),XmlArrayItem("item")] public Cat[] Cats { get; set; } } [XmlRoot("cat")] public class Cat { //定义Color属性的序列化为cat节点的属性 [XmlAttribute("color")] public string Color { get; set; } //要求不序列化Speed属性 [XmlIgnore] public int Speed { get; set; } //设置Saying属性序列化为Xml子元素 [XmlElement("saying")] public string Saying { get; set; } } }
最终获得的结果是:
<?xml version="1.0" encoding="gb2312"?> <cats xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> <items> <item color="White"> <saying>White or black, so long as the cat can catch mice, it is a good cat</saying> </item> <item color="Black"> <saying>White or black, so long as the cat can catch mice, it is a good cat</saying> </item> </items> </cats>
以上就是详解 C# 中XML对象的序列化和反序列化的详细内容,更多关于c# xml序列化和反序列化的资料请关注小牛知识库其它相关文章!
本文向大家介绍详解Java 对象序列化和反序列化,包括了详解Java 对象序列化和反序列化的使用技巧和注意事项,需要的朋友参考一下 之前的文章中我们介绍过有关字节流字符流的使用,当时我们对于将一个对象输出到流中的操作,使用DataOutputStream流将该对象中的每个属性值逐个输出到流中,读出时相反。在我们看来这种行为实在是繁琐,尤其是在这个对象中属性值很多的时候。基于此,Java中对象的序列
本文向大家介绍Java中对象序列化与反序列化详解,包括了Java中对象序列化与反序列化详解的使用技巧和注意事项,需要的朋友参考一下 本文实例讲述了Java中对象序列化与反序列化。分享给大家供大家参考。具体如下: 一、简介 对象序列化(Serializable)是指将对象转换为字节序列的过程,而反序列化则是根据字节序列恢复对象的过程。 序列化一般用于以下场景: 1.永久性保存对象,保存对象的字节序列
本文向大家介绍.Net中的序列化和反序列化详解,包括了.Net中的序列化和反序列化详解的使用技巧和注意事项,需要的朋友参考一下 序列化和反序列化相信大家都经常听到,也都会用, 然而有些人可能不知道:.net为什么要有这个东西以及.net Frameword如何为我们实现这样的机制, 在这里我也是简单谈谈我对序列化和反序列化的一些理解。 一、什么序列化和反序列化 序列化通俗地讲就是将一个对象转换成一
我想序列化一些XML。我的代码运行正常,但序列化不成功,对象为空,而不是填充数据。该值只是类型值:{OrangeCdToCollectorz.OrangeCd}。我怀疑我的阶级定义。以下是我正在序列化的类: 这是我的代码,尝试使用几种众所周知的技术对相同的XML进行反序列化,无论是作为字符串const还是来自文件: 以下是源XML的示例
本文向大家介绍java对象的序列化和反序列化,包括了java对象的序列化和反序列化的使用技巧和注意事项,需要的朋友参考一下 本文实例为大家分享了java对象的序列化和反序列化,供大家参考,具体内容如下 1. 什么是序列化 将对象转换为字节流保存起来,比如保存到文件里,并在以后还原这个对象,这种机制叫做对象序列化。(补充一句:把对象保存到永久存储设备上称为持久化) 2. 怎么实现序列化
本文向大家介绍java 对象的序列化和反序列化详细介绍,包括了java 对象的序列化和反序列化详细介绍的使用技巧和注意事项,需要的朋友参考一下 最近周末,对java 的基础知识做了一个整理,其中java 序列化和反序列化的资料进行了详细整理,这里做个笔记,希望也能帮助到读到此文的朋友。 一、序列化和反序列化的概念 把对象转换为字节序列的过程称为对象的序列化。 把字节序列恢复为对象