C# XML deserialization

邮差的信 提交于 2020-02-06 02:43:30

问题


I have xml that is returned with an array of different types of objects. I am having trouble with the xmlchoiceidentifier when it gets to the keyword struct. When it deserializes it, it just returns null.

Here is the xml that I am trying to deserialize:

<struct>
   <member>
      <name>result</name>
      <value><boolean>1</boolean></value>
   </member>
   <member>
      <name>user_info</name>
      <value>
         <struct>
            <member>
               <name>First Name</name>
               <value><string>John</string></value>
            </member>
            <member>
               <name>Last Name</name>
               <value><string>Smith</string></value>
            </member>
         </struct>
      </value>
   </member>
</struct>

Here is the code I have for deserialization:

public class ResponseStruct
{
    [XmlArray("struct"), XmlArrayItem("member")]
    public List<ResponseMember> Struct { get; set; }
}

public class ResponseArray
{
    [XmlArray("array"), XmlArrayItem("data")]
    public List<ResponseMemberValue> Array { get; set; }
}

public class ResponseMember
{
    [XmlElement("name")]
    public string Name { get; set; }

    [XmlElement("value")]
    public ResponseMemberValue Value { get; set; }
}

public class ResponseMemberValue
{
    [XmlChoiceIdentifier("ValueChoice"), XmlElement("boolean", typeof(bool)), XmlElement("int", typeof(int)), XmlElement("string", typeof(string)), XmlElement("datetime", typeof(DateTime)), XmlElement("double", typeof(double)), XmlElement("base64", typeof(string)), XmlElement("array", typeof(ResponseArray)), XmlElement("struct", typeof(ResponseStruct))]
    public object Value { get; set; }

    [XmlIgnore]
    public virtual ValueType ValueChoice { get; set; }

    public enum ValueType
    {
        @string,
        @int,
        @datetime,
        @double,
        base64,
        array,
        boolean,
        @struct
    }
}

回答1:


Your main problem is that you have specified [XmlArray("struct"), XmlArrayItem("member")] for public List<ResponseMember> Struct { get; set; }. This means that the XML for this collection should have an outer wrapper element named <struct>. However, an outer <struct> element is also specified by the XmlElement("struct", typeof(ResponseStruct)) attribute on the containing ResponseMemberValue.Value property - but your XML has only one level of <struct> elements. Thus you need to specify that this collection does not have an outer container element, by using [XmlElement("member")]. And, while your XML does not include a sample of the <array> element, I suspect you should do the same for ResponseArray also.

Next, you need to specify the root element name using [XmlRoot] or [XmlType]. If you use the latter, it will be used automatically as the element name in the polymorphic Value element.

Thus:

[XmlType("struct")]
public class ResponseStruct
{
    [XmlElement("member")]
    public List<ResponseMember> Struct { get; set; }
}

[XmlType("array")]
public class ResponseArray
{
    [XmlElement("data")]
    public List<ResponseMemberValue> Array { get; set; }
}

public class ResponseMember
{
    [XmlElement("name")]
    public string Name { get; set; }

    [XmlElement("value")]
    public ResponseMemberValue Value { get; set; }
}

public class ResponseMemberValue
{
    [XmlChoiceIdentifier("ValueChoice")]
    [XmlElement("boolean", typeof(bool)), 
    XmlElement("int", typeof(int)), 
    XmlElement("string", typeof(string)), 
    XmlElement("datetime", typeof(DateTime)), 
    XmlElement("double", typeof(double)), 
    XmlElement("base64", typeof(string)), 
    XmlElement(typeof(ResponseArray)), 
    XmlElement(typeof(ResponseStruct))]
    public object Value { get; set; }

    [XmlIgnore]
    public virtual ValueType ValueChoice { get; set; }

    public enum ValueType
    {
        @string,
        @int,
        @datetime,
        @double,
        base64,
        array,
        boolean,
        @struct
    }
}

Prototype fiddle.



来源:https://stackoverflow.com/questions/37229202/c-sharp-xml-deserialization

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!