使用父标记序列化基类的列表
本文关键字:列表 基类 序列化 | 更新日期: 2023-09-27 18:33:44
我似乎能够在网上找到试图避免这种行为的人,但我似乎无法得到我想要的行为。
我有一个动物列表,我想为每个动物类型使用不同的标签对它们进行序列化(而不是带有附加属性的默认 beahviour)
为了获得这种行为,我使用以下代码
[XmlElementAttribute(Order = 4)]
[XmlElement("Frog", typeof(Frog))]
[XmlElement("Cat", typeof(Cat))]
[XmlElement("Dog", typeof(Dog))]
public List<Animal> lines = new List<Animal>();
这很好用,除了它扁平化了列表,如果 xml 输出更像,我更喜欢它 <animals>
<Dog>Bob</Dog>
<Cat>Fred</Cat>
<Dog>Mike</Dog>
</animals>
保留<animals>
标签
更改[XmlArrayAttribute(Order=4)]
的[XmlElementAttribute(Order = 4)]
您还可以在属性中指定一个ElementName
参数,该参数将是根名称,即:[XmlArrayAttribute(Order=4, ElementName="animals")]
*注意:Order=4 是这种情况的特殊情况。你通常不需要它。*
编辑:(感谢OP评论):
您还必须将属于列表的对象类的属性从[XmlElement]
更改为[XmlArrayItem]
(此处为 MSDN 文档),如下所示:
[XmlArrayItem("Frog", typeof(Frog))]
[XmlArrayItem("Cat", typeof(Cat))]
[XmlArrayItem("Dog", typeof(Dog))]
您始终可以将列表包装在其自己的类中,您将获得所需的 XML:
public class StackOverflow_10524470
{
public class Animal
{
[XmlText]
public string Name { get; set; }
}
public class Dog : Animal { }
public class Cat : Animal { }
public class Frog : Animal { }
public class Root
{
[XmlElementAttribute(Order = 4, ElementName = "animals")]
public Animals animals;
}
public class Animals
{
[XmlElementAttribute(Order = 4)]
[XmlElement("Frog", typeof(Frog))]
[XmlElement("Cat", typeof(Cat))]
[XmlElement("Dog", typeof(Dog))]
public List<Animal> lines = new List<Animal>();
}
public static void Test()
{
MemoryStream ms = new MemoryStream();
XmlSerializer xs = new XmlSerializer(typeof(Root));
Root root = new Root
{
animals = new Animals
{
lines = new List<Animal>
{
new Dog { Name = "Fido" },
new Cat { Name = "Fluffy" },
new Frog { Name = "Singer" },
}
}
};
xs.Serialize(ms, root);
Console.WriteLine(Encoding.UTF8.GetString(ms.ToArray()));
}
}