防止IEnumerable和ICollection的XML序列化<t>&amp;继承类型</t>

时间:2008-08-28 07:36:40

标签: xml inheritance serialization .net-2.0

注意: XMLIgnore 不是答案!

好的,继续我在XML Serialization and Inherited Types的问题后,我开始将该代码集成到我正在处理的应用程序中,愚蠢地认为一切都会顺利进行..

我遇到了几个我实现 IEnumerable ICollection&lt; T&gt;

的类的问题

这些问题是当XMLSerializer来序列化这些时,它会将它们视为外部属性,而不是使用我们希望的属性(即使用我们的 AbstractXmlSerializer 的属性)它来到这里并摔倒(由于类型不匹配),几乎把我们放回原点。你不能用 XmlIgnore 属性来装饰这些方法,所以我们不能那样阻止它。

我目前的解决方案是删除接口实现(在当前的应用程序中,它没有什么大不了的,只是使代码更漂亮)。

我是否需要吞下我对这一个的骄傲并接受它无法完成?我知道我有点推动并从XmlSerializer中获得了比预期更多的东西:)


修改

我还应补充一点,我目前正在使用框架2。


更新

我接受了lomaxx's answer。在我的场景中,我实际上无法做到这一点,但我知道它会起作用。由于他们没有其他建议,我最终从代码中删除了接口实现。

3 个答案:

答案 0 :(得分:4)

您可以通过获取System.RunTime.Serialization dll(它是.net 3.x程序集)并从.net 2.0应用程序引用它来解决此问题。这是有效的,因为.net 3.0二进制文件被编译为在.net 2.0 CLR上运行。

通过这样做,您可以访问DataContractSerliazer,我曾经习惯于解决类似的问题,我想将ICollection作为参数传递给Web服务,而xmlserializer不知道如何处理它正常。

如果你在2.x应用程序中使用.net 3.x dll很酷,你应该可以使用DataContractSerializer来解决这个问题

答案 1 :(得分:3)

我想答案来得太晚,无法对您的特定应用程序有用,但也许还有其他人遇到同样的问题。

我想你可以为IEnumerable类型实现IXmlSerializable来解决这个问题。但是,这意味着您必须完全控制此类型的序列化过程。一个简单的方法,不必乱用XmlReader / XmlWriter,您可以编写一个帮助xml适配器类与公共ctor和所有要序列化的数据的公共读写属性,并在此内部为此类型创建一个临时XmlSerializer对象IXmlSerializable的。[读取|写入] XML()

class Target : IEnumerable<Anything>, IXmlSerializable
{
//...

public void ReadXml(System.Xml.XmlReader reader)
{
    reader.ReadStartElement();
    TargetXmlAdapter toRead = (TargetXmlAdapter)new XmlSerializer(typeof(TargetXmlAdapter)).Deserialize(reader);
    reader.Read();

    // here: install state from TargetXmlAdapter
}

public void WriteXml(System.Xml.XmlWriter writer)
{
    // NOTE: TargetXmlAdapter(Target) is supposed to store this' state being subject to serialization
    new XmlSerializer(typeof(TargetXmlAdapter)).Serialize(writer, new TargetXmlAdapter(this));
}
}

答案 2 :(得分:1)

如果您使用以下属性:

        [XmlArray("ProviderPatientLists")]
        [XmlArrayItem("File")]
      public ProviderPatientList Files
    {
        get { return _ProviderPatientLists; }
        set
        {
            _ProviderPatientLists = value;
        }
    }

ProviderPatientList继承List<PatientList>

的位置

然后,您可以更多地控制xml输出 将创建