使用C#将XmlArrayAttribute行的XML文档反序列化为对象

时间:2014-08-15 14:14:24

标签: c# xml serialization deserialization xml-deserialization

我有一个如下所示的XML:

<document>
    (...)
    <flex>
        <attrGroupMany name="foodAndBev">
            <row>
                <attr name="agency">ASA EACH CASE36</attr>
                <attrQualMany name="ingredientsList">
                  <value qual="en">IL EACH CASE3688s</value>
                  <value qual="en">IL TEST</value>
                  <value qual="en">IL TEST2</value>
                </attrQualMany>
            </row>
            <row>
                <attr name="agency">ASA EACH CASE36</attr>
                <attrQualMany name="ingredientsList">
                  <value qual="en">IL EACH CASE3688s</value>
                  <value qual="en">IL TEST</value>
                  <value qual="en">IL TEST2</value>
                </attrQualMany>
            </row>
        </attrGroupMany>
        <attr name="FlexType">food</attr>
    </flex>
</document>

为了将这个XML反序列化为一个类,我创建了以下结构:

Document类看起来像这样:

public class document
{
        (...)
        [System.Xml.Serialization.XmlArrayAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified, Order = 158)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attr", typeof(AttrRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrMany", typeof(AttrRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrQual", typeof(AttrQualRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrQualMany", typeof(AttrQualRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrQualOpt", typeof(AttrQualOptRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrQualOptMany", typeof(AttrQualOptRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrGroup", typeof(AttrGroupType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlArrayItemAttribute("attrGroupMany", typeof(AttrGroupManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        public List<object> flex
        {
            get
            {
                return this._flex;
            }
            set
            {
                this._flex = value;
            }
        }
}

AttrGroupManyType课程如下:

public class AttrGroupManyType
{
    [System.Xml.Serialization.XmlAttributeAttribute()]
    public string name { get; set; }

    [System.Xml.Serialization.XmlArrayAttribute("row", Form = System.Xml.Schema.XmlSchemaForm.Unqualified)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attr", typeof(AttrRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrMany", typeof(AttrRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrQual", typeof(AttrQualRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrQualMany", typeof(AttrQualRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrQualOpt", typeof(AttrQualOptRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrQualOptMany", typeof(AttrQualOptRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrGroup", typeof(AttrGroupType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    [System.Xml.Serialization.XmlArrayItemAttribute("attrGroupMany", typeof(AttrGroupManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
    public List<object> row { get; set; }
}

更新

以这种方式定义 AttrGroupManyType 时,我能够在XML字符串和Document类型的对象之间反序列化/序列化,但我不能得到多个attrGroupMany

所有属性都合并为一行

例如:foodAndBev,最初具有以下结构:

[row0] => { agency, ingredientsList }

[row1] => { agency, ingredientsList }

获取序列化为:

[row0] => { agency, ingredientsList, agency, ingredientsList }

另外,如果我将row属性的dataType从List<object>更改为object[] 我只得到第一行中的数据,重复的属性不会进入输出xml。

对于上面的例子,我只得到:

[row0] => { agency, ingredientsList }

我的问题是:

如何更改类实现,以便能够对 attrGroupMany 节点内的原始数据进行反序列化/序列化,即使存在多个row

2 个答案:

答案 0 :(得分:1)

不确定我是否理解了您的问题,但请尝试查看MSDN上的XmlWriterSettingsXmlReaderSettings类。有一些名为Indent和NewLineChars的属性可能会帮助您格式化。

答案 1 :(得分:0)

第一次尝试。 XSD 工具

<小时/> 我尝试通过键入xsd /c file.xsd创建 C#类,因为我有生成的XML的架构,但是,此方法不起作用,因为xsd.exe始终返回以下错误:< p>

  

Microsoft(R)Xml架构/数据类型支持实用程序[Microsoft(R)   .NET Framework,版本4.0.30128.1]版权所有(C)Microsoft   公司。所有权利保留

     

由于StackOverflowException,进程终止。

但是,考虑到您在 XSD 架构中可能没有疯狂的“flex”结构,这种方法可能适合您。

第二次尝试 - 粘贴特殊(成功)

<小时/> 必需的Visual Studio 2012 +

  1. 将XML文件的内容复制到剪贴板
  2. 向您的解决方案添加新的空类文件( Shift + Alt + C
  3. 打开该文件,然后在菜单中点击Edit > Paste special > Paste XML As Classes
    enter image description here
  4. 就是这样!

    经过一些小的修改后,生成的类看起来像这样:


    Document课程

    public class document
    {
        (...)
        [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)]
        public Flex flex
        {
            get
            {
                return this._flex;
            }
            set
            {
                this._flex = value;
            }
        }
    } 
    

    AttrGroupManyType课程

    public class AttrGroupManyType
    {
        (...)
    
        [System.Xml.Serialization.XmlElementAttribute("row", typeof(Flex), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        public List<Flex> row
        {
            get
            {
                return this._row;
            }
            set
            {
                this._row = value;
            }
        }
    }
    

    最后,新的Flex类:

    public class Flex
    {
        public Flex()
        {
            itemsField = new List<object>();
        }
    
        public Flex(object item) : this()
        {
            itemsField.Add(item);
        }
    
        private List<object> itemsField;
    
        [System.Xml.Serialization.XmlElementAttribute("attr", typeof(AttrRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrMany", typeof(AttrRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrQual", typeof(AttrQualRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrQualMany", typeof(AttrQualRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrQualOpt", typeof(AttrQualOptRddType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrQualOptMany", typeof(AttrQualOptRddManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrGroup", typeof(AttrGroupType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        [System.Xml.Serialization.XmlElementAttribute("attrGroupMany", typeof(AttrGroupManyType), Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = false)]
        public List<object> Items
        {
            get
            {
                return this.itemsField;
            }
            set
            {
                this.itemsField = value;
            }
        }
    }