XmlSerializer:如何反序列化不再存在的枚举值

我正在使用XMLSerializer将此类保存到文件中。 该类有一个字符串和一个枚举,如下所示:

public class IOPoint { string Name {get; set;} TypeEnum {get; set;} } public enum TypeEnum { Temperature, Pressure, Humidity, } 

序列化时,它看起来像这样。

  Relative Humidity Humidity  

我一直在序列化和反序列化这个对象,几个版本都没有问题。 我不再想支持湿度,所以我将它从枚举中删除了。 但是,这会在从XML反序列化时导致exception,因为TypeEnum字段中的值Humidity不是TypeEnum的有效值。 这是有道理的,但如何处理呢?

我想做的就是忽略这个错误。 并将值保留为null。 我已经尝试实现OnUnknownElement XmlDeserilizationEvent类。 不幸的是,这并没有发现这个错误。

关于如何捕获和忽略此错误的任何想法(我可以在反序列化完成后清理)。

米奇

您可以将成员标记为已过时

 public enum TypeEnum { Temperature, Pressure, [Obsolete] Humidity } 

在您的库已被使用后删除枚举成员通常被认为是不好的做法。 为什么不将会员留在原地,而是使用[Obsolete]属性标记以防止将来使用? 如果访问标记的成员ObsoleteAttribute(string,bool)则将ObsoleteAttribute(string,bool)构造函数的第二个参数指定为true将导致编译时错误。

 public enum TypeEnum { Temperature, Pressure, [Obsolete("It's always sunny in Philadelphia", true)] Humidity, } 

要在检查反序列化值时避免错误,可以与基础值进行比较: typeEnum == (TypeEnum)2

您可以使用属性来更改节点名称并隐藏xml序列化中的元素,只需手动解析一个元素:

 public class IOPoint { public string Name {get; set;} [XmlIgnore] public TypeEnum TypeEnum {get; set;} [XmlElement("TypeEnum")] public string LegacyTypeEnum { get { return this.TypeEnum.ToString(); } set { try { this.TypeEnum = (TypeEnum)Enum.Parse(typeof(TypeEnum),value); } catch(ArgumentException) { // Handle "Humidity" } catch(OverflowException) { } } } } 

每条评论似乎都有些混乱; 这是一个作为Visual Studio 2010项目的工作示例 。 这种方法只是手动解析对象的一个​​属性的简单方法(仍然利用XmlSerializer进行XML解析)。

你可以实现IXmlSerializable ,你可以在其中使用像TryParse这样的枚举。

但我同意使用Obsolete属性的其他海报。