当类从List<>继承时,XmlSerializer不会序列化其他属性

时间:2011-02-21 17:22:39

标签: c# .net list xml-serialization ienumerable

我遇到了这种情况,我需要从List<ItemType>继承我的类,但是当我这样做时,XmlSerializer不会序列化我的类中声明的任何属性或字段,下面的示例演示:

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
        DoSerialize();
    }
    private void DoSerialize()
    {
        MyClass obj = new MyClass();
        obj.Add(1);
        obj.Add(2);
        obj.Add(3);
        XmlSerializer s = new XmlSerializer(typeof(MyClass));
        StringWriter sw = new StringWriter();
        s.Serialize(sw, obj);
    }
}
[Serializable]
[XmlRoot]
public class MyClass : List<int>
{
    public MyClass()
    {
    }
    int myAttribute = 2011;
    [XmlAttribute]
    public int MyAttribute
    {
        get
        {
            return myAttribute;
        }
        set
        {
            myAttribute = value;
        }
    }
}

生成的XML:

<?xml version="1.0" encoding="utf-16"?>
<ArrayOfInt xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <int>1</int>
  <int>2</int>
  <int>3</int>
</ArrayOfInt>

2 个答案:

答案 0 :(得分:23)

这是设计的。我不知道为什么做出这个决定,but it is stated in the documentation

  
      
  • 实现ICollection或IEnumerable的类。只有收藏品   序列化的,而不是公共财产。
  •   

(查看“可以序列化的项目”部分)。 Someone has filed a bug against this, but it won't be changed - 在这里,Microsoft还确认不包括实现ICollection的类的属性实际上是XmlSerializer的行为。

解决方法是:

  • 实施IXmlSerializable并自行控制序列化。

  • 更改MyClass,使其具有List类型的公共属性(不要将其子类化)。

  • 使用DataContractSerializer处理此方案。

答案 1 :(得分:3)

这是一个让你考虑的问题。

你可以拥有一个像这样的容器类的类:

class ContainerObject
{
     public int MyNewProperty { get; set; }

     [XmlElement("")]
     public List<int> MyList { get; set; }
}

诀窍是在List元素上面有XmlElement name =“”。

当将其序列化为xml时,您将拥有:

<ContainerObject>
   <MyNewProperty>...</MyNewProperty>

   <int>...</int>
   <int>...</int>

</ContainerObject>

如果您愿意,还可以为列表中的项目创建另一个类

 class MyItem
 {
     public int MyProperty {get;set;} 

 } 

然后不是拥有整数列表,而是拥有一个MyItems列表。

这是您控制列表中每个项目的XmlElement名称。

我希望这很有帮助。