建议55:利用定制特性减少可序列化的字段

来源:互联网 发布:淘宝图片轮播制作 编辑:程序博客网 时间:2024/06/05 00:34

建议55:利用定制特性减少可序列化的字段

特性(attribute)可以声明式地为代码中的目标元素添加注释。运行时可以通过查询这些托管块中的元数据信息,达到改变目标元素运行时行为的目的。System.Runtime.Serialization命名空间下,有4个这样的特性:

  • OnDeserializedAttribute,当它应用于某方法时,会指定在对象反序列化后立即调用此方法。
  • OnDeserializingAttribute,当他应用于某方法,会指定在反序列化对象时调用此方法。
  • OnSerializedAttribute,当它应用于某方法时,会指定在对象序列化后立即调用此方法。
  • OnSerializingAttribute,当他应用于某方法,会指定在序列化对象时调用此方法。

利用这些特性,可以更加灵活地处理序列化和反序列化。例如,我们可以利用这一点,进一步减少某些可序列化的字段。

Person类由ChineseName、FirstName、LastName字段组成:

复制代码
    [Serializable]    class Person    {        public string FirstName;        public string LastName;        public string ChineseName;    }
复制代码

我们知道,ChineseName实际可以有FirstName和LastName推断出,所以这意味着ChineseName不需要被序列化。这时候,我们就可以利用特性,提供一个方法在序列化完成后计算ChineseName的值:

复制代码
    class Program    {        static void Main()        {            Person liming = new Person() { FirstName = "Ming", LastName = "Li", ChineseName = "Li Ming" };            BinarySerializer.SerializeToFile(liming, @"c:\", "Person.txt");            Person person = BinarySerializer.DeserializeFromFile<Person>(@"c:\Person.txt");            Console.WriteLine(person.ChineseName);        }    }    [Serializable]    class Person    {        public string FirstName;        public string LastName;        [NonSerialized]        public string ChineseName;        [OnDeserializedAttribute]        void OnSerialized(StreamingContext context)        {            ChineseName = string.Format("{0} {1}", LastName, FirstName);        }    }
复制代码

序列化工具类:

复制代码
    public class BinarySerializer    {        //将类型序列化为字符串        public static string Serialize<T>(T t)        {            using (MemoryStream stream = new MemoryStream())            {                BinaryFormatter formatter = new BinaryFormatter();                formatter.Serialize(stream, t);                return System.Text.Encoding.UTF8.GetString(stream.ToArray());            }        }        //将类型序列化为文件        public static void SerializeToFile<T>(T t, string path, string fullName)        {            if (!Directory.Exists(path))            {                Directory.CreateDirectory(path);            }            string fullPath = Path.Combine(path, fullName);            using (FileStream stream = new FileStream(fullPath, FileMode.OpenOrCreate))            {                BinaryFormatter formatter = new BinaryFormatter();                formatter.Serialize(stream, t);                stream.Flush();            }        }        //将字符串反序列化为类型        public static TResult Deserialize<TResult>(string s) where TResult : class        {            byte[] bs = System.Text.Encoding.UTF8.GetBytes(s);            using (MemoryStream stream = new MemoryStream(bs))            {                BinaryFormatter formatter = new BinaryFormatter();                return formatter.Deserialize(stream) as TResult;            }        }        //将文件反序列化为类型        public static TResult DeserializeFromFile<TResult>(string path) where TResult : class        {            using (FileStream stream = new FileStream(path, FileMode.Open))            {                BinaryFormatter formatter = new BinaryFormatter();                return formatter.Deserialize(stream) as TResult;            }        }    }
复制代码

 

 

 

 

转自:《编写高质量代码改善C#程序的157个建议》陆敏技

0 0
原创粉丝点击