经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » C# » 查看文章
C#序列化与反序列化集合对象并进行版本控制
来源:jb51  时间:2022/9/15 9:09:17  对本文有异议

当涉及到跨进程甚至是跨域传输数据的时候,我们需要把对象序列化和反序列化。

首先可以使用Serializable特性。

  1. [Serializable]
  2. public class Person
  3. {
  4. public string _firstName;
  5. public string _secondName;
  6. //序列化
  7. [OnSerializing]
  8. internal void OnSerializing(StreamingContext context)
  9. {
  10. _firstName = _firstName.ToUpper();
  11. _secondName = _secondName.ToUpper();
  12. }
  13. //反序列化
  14. [OnDeserialized]
  15. internal void OnDeserialized(StreamingContext context)
  16. {
  17. _firstName = _firstName.ToLower();
  18. _secondName = _secondName.ToLower();
  19. }
  20. }

当然,也可以实现ISerializable接口。在接口方法GetObjectData完成序列化,把信息保存到SerializationInfo中,在构造函数中反序列化,把信息从SerializationInfo中读取出来。

  1. [Serializable]
  2. public class Person : ISerializable
  3. {
  4. public string _firstName;
  5. public string _secondName;
  6. public Person()
  7. {
  8. }
  9. //反序列化
  10. public Person(SerializationInfo si, StreamingContext context)
  11. {
  12. _firstName = si.GetString("first").ToLower();
  13. _secondName = si.GetString("second").ToLower();
  14. }
  15. //序列化
  16. public void GetObjectData(SerializationInfo info, StreamingContext context)
  17. {
  18. info.AddValue("first", _firstName.ToUpper());
  19. info.AddValue("second",_secondName.ToUpper());
  20. }
  21. }

对序列化和反序列化对象进行版本控制

下面的类,描述了对象的第一个版本。

  1. [Serializable]
  2. public class SomeClass : ISerializable
  3. {
  4. private int a;
  5. public SomeClass(){}
  6. public SomeClass(SerializationInfo info, StreamingContext context)
  7. {
  8. a = info.GetInt32("myval");
  9. }
  10. public void GetObjectData(SerializationInfo, StreamingContext context)
  11. {
  12. info.AddValue("VERSION",1);
  13. info.AddValue("myval", a);
  14. }
  15. }

现在SomeClass要增加一个私有字段,成为版本二。

  1. [Serializable]
  2. public class SomeClass : ISerializable
  3. {
  4. private int a;
  5. private string b;
  6. public SomeClass(){}
  7. public SomeClass(SerializationInfo info, StreamingContext context)
  8. {
  9. int VERSION = info.GetInt32("VERSION");
  10. a = info.GetInt32("a");
  11. if(VERSION > 1)
  12. {
  13. b = info.GetString("another");
  14. }
  15. else
  16. {
  17. b = "默认值";
  18. }
  19. }
  20. public void GetObjectData(SerializationInfo, StreamingContext context)
  21. {
  22. info.AddValue("VERSION",2);
  23. info.AddValue("myval", a);
  24. info.AddValue("another", b);
  25. }
  26. }

把集合对象序列化到文件并反序列化读出

如果一个集合对象需要实现序列化和反序列化,那么集合元素对象必须可以被序列化和反序列化,并且集合元素对象中的对象属性也必须可以被序列化和反序列化,依此类推。

  1. [Serializable]
  2. public class Car : ISerializable
  3. {
  4. private string _model;
  5. private int _year;
  6. private Owner _owner;
  7. public Car()
  8. {
  9. }
  10. public Car(SerializationInfo info, StreamingContext context)
  11. {
  12. this._model = (string) info.GetValue("Model", typeof (string));
  13. this._year = (int) info.GetValue("Year", typeof (int));
  14. this._owner = (Owner) info.GetValue("Owner", typeof (Owner));
  15. }
  16. public void GetObjectData(SerializationInfo info, StreamingContext context)
  17. {
  18. info.AddValue("Model",this._model);
  19. info.AddValue("Year", this._year);
  20. info.AddValue("Owner", this._owner);
  21. }
  22. }
  23. [Serializable]
  24. public class Owner : ISerializable
  25. {
  26. private string _name;
  27. public Owner()
  28. {
  29. }
  30. public Owner(SerializationInfo info, StreamingContext context)
  31. {
  32. this._name = (string) info.GetValue("Name", typeof (string));
  33. }
  34. public void GetObjectData(SerializationInfo info, StreamingContext context)
  35. {
  36. info.AddValue("Name", this._name);
  37. }
  38. }

以上,我们想序列化Car的集合到文件中,再反序列化Cars的集合读取出来。那么,我们必须让Car可以被序列化和反序列化,Car的属性对象Owner也必须可以被序列化和反序列化。

接着,用来封装Car集合的一个类。

  1. [Serializable]
  2. public class CarsList : ISerializable
  3. {
  4. private List<Car> _cars;
  5. public List<Car> Cars
  6. {
  7. get { return this._cars; }
  8. set { this._cars = value; }
  9. }
  10. public CarsList()
  11. {
  12. }
  13. public CarsList(SerializationInfo info, StreamingContext context)
  14. {
  15. this._cars = (List<Car>) info.GetValue("Cars", typeof (List<Car>));
  16. }
  17. public void GetObjectData(SerializationInfo info, StreamingContext context)
  18. {
  19. info.AddValue("Cars", this._cars);
  20. }
  21. }

针对CarsList写一个序列化和反序列化的帮助类。

  1. public class SerializerHelper
  2. {
  3. public SerializerHelper()
  4. {
  5. }
  6. //序列化
  7. public void SerializeObject(string fileName, CarsList carsList)
  8. {
  9. //根据文件名打开流
  10. Stream stream = File.Open(fileName, FileMode.Create);
  11. BinaryFormatter bFormatter = new BinaryFormatter();
  12. //把对象序列化到流中
  13. bFormatter.Serialize(stream,carsList);
  14. stream.Close();
  15. }
  16. //反序列化
  17. public CarsList DeserializeObject(string fileName)
  18. {
  19. CarsList carsList;
  20. //根据文件名打开流
  21. Stream stream = File.Open(fileName, FileMode.Open);
  22. BinaryFormatter bfFormatter = new BinaryFormatter();
  23. carsList = (CarsList)bfFormatter.Deserialize(stream);
  24. stream.Close();
  25. return carsList;
  26. }
  27. }

在客户端按如下调用:

  1. static void Main(string[] args)
  2. {
  3. List<Car> cars = new List<Car>();
  4. CarsList carsList = new CarsList();
  5. carsList.Cars = cars;
  6. SerializerHelper serializerHelper = new SerializerHelper();
  7. serializerHelper.SerializeObject(@"temp.txt", carsList);
  8. carsList = serializerHelper.DeserializeObject(@"temp.txt");
  9. cars = carsList.Cars;
  10. }

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,谢谢大家对w3xue的支持。如果你想了解更多相关内容请查看下面相关链接

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号