2016-06-09 316 views
0

我试图反序列化API响应中返回的一些XML,但反序列化后,对象中的所有值都是NULL。C#:反序列化XML后的对象值为空

下面是我正在尝试反序列化的响应XML。

<?xml version="1.0" encoding="utf-8"?> 
<ctatt> 
    <tmst>20160609 11:50:03</tmst> 
    <errCd>0</errCd> 
    <errNm /> 
    <eta> 
     <staId>41300</staId> 
     <stpId>30252</stpId> 
     <staNm>Loyola</staNm> 
     <stpDe>Service toward 95th/Dan Ryan</stpDe> 
     <rn>803</rn> 
     <rt>Red</rt> 
     <destSt>30089</destSt> 
     <destNm>95th/Dan Ryan</destNm> 
     <trDr>5</trDr> 
     <prdt>20160609 11:48:45</prdt> 
     <arrT>20160609 11:51:45</arrT> 
     <isApp>0</isApp> 
     <isSch>0</isSch> 
     <isDly>0</isDly> 
     <isFlt>0</isFlt> 
     <flags /> 
     <lat>42.01906</lat> 
     <lon>-87.67289</lon> 
     <heading>130</heading> 
    </eta> 
</ctatt> 

这里是我的类:

[Serializable, XmlRoot("ctatt")] 
     public class trainData 
     { 
      [XmlElement(ElementName ="tmst")] 
      public string timeStamp { get; set; } 

      [XmlElement(ElementName = "errCd")] 
      public byte errorCode { get; set; } 

      [XmlElement(ElementName = "staId")] 
      public ushort stationId { get; set; } 

      [XmlElement(ElementName = "stpId")] 
      public ushort stopId { get; set; } 

      [XmlElement(ElementName = "staNm")] 
      public string stationName { get; set; } 

      [XmlElement(ElementName = "stpDe")] 
      public string stopDesc { get; set; } 

      [XmlElement(ElementName = "rn")] 
      public ushort runNum { get; set; } 

      [XmlElement(ElementName = "rt")] 
      public string routeName { get; set; } 

      [XmlElement(ElementName = "destSt")] 
      public ushort destStation { get; set; } 

      [XmlElement(ElementName = "destNm")] 
      public string destName { get; set; } 

      [XmlElement(ElementName = "trDr")] 
      public byte trainDir { get; set; } 

      [XmlElement(ElementName = "prdt")] 
      public string prdTime {get; set;} 

      [XmlElement(ElementName = "arrT")] 
      public string arrTime { get; set; } 

      [XmlElement(ElementName = "isApp")] 
      public ushort isApp { get; set; } 

      [XmlElement(ElementName = "isSch")] 
      public ushort isSch { get; set; } 

      [XmlElement(ElementName = "isDly")] 
      public ushort isDly { get; set; } 

      [XmlElement(ElementName = "isFlt")] 
      public ushort isFlt { get; set; } 

      [XmlElement(ElementName = "flags")] 
      public string flags { get; set; } 

      [XmlElement(ElementName = "lat")] 
      public double lat { get; set; } 

      [XmlElement(ElementName = "lon")] 
      public double lon { get; set; } 

      [XmlElement(ElementName = "heading")] 
      public ushort heading { get; set; } 
     } 

这里是我使用的反序列化的代码:

var response = await client.GetAsync(urlParameters); 
       if (response.IsSuccessStatusCode) 
       { 
        var xml = await response.Content.ReadAsStringAsync(); 
        XmlSerializer deserializer = new XmlSerializer(typeof(trainData)); 
        using (StringReader reader = new StringReader(xml)) 
        { 
         using (XmlReader xr = XmlReader.Create(reader)) 
         { 
          trainData result = (trainData)deserializer.Deserialize(xr); 
          Console.WriteLine("Station Name: {0}\nRoute Name: {1}\nArrival Time: {2}", result.stationName, result.routeName, result.arrTime); 
         } 
        } 
       } 
       else 
       { 
        Console.WriteLine("There was an error!"); 
       } 

任何建议,将不胜感激...

+0

你还应该包括你正在获取的堆栈跟踪。 –

+1

'trainData'需要一个'eta'类型作为属性。这些嵌套在'eta'中的元素不能在'trainData'上反序列化。 – Crowcoder

回答

2

您提供的xml有2层ctatteta。然而你的模型只有一个层次。当然这不会起作用。

你需要改变你的模型保持布局相同与XML:

[Serializable, XmlRoot("ctatt")] 
public class trainDataResult 
{ 
    [XmlElement(ElementName ="tmst")] 
    public string timeStamp { get; set; } 

    [XmlElement(ElementName = "errCd")] 
    public byte errorCode { get; set; } 

    // uncomment next lines to include `errNm` 
    //[XmlElement(ElementName = "errNm")] 
    //public string errorName { get; set; } 

    [XmlElement(ElementName = "eta")] 
    public TrainData eta { get; set; } 
} 

public class TrainData 
{ 
    [XmlElement(ElementName = "staId")] 
    public ushort stationId { get; set; } 

    [XmlElement(ElementName = "stpId")] 
    public ushort stopId { get; set; } 

    [XmlElement(ElementName = "staNm")] 
    public string stationName { get; set; } 

    [XmlElement(ElementName = "stpDe")] 
    public string stopDesc { get; set; } 

    [XmlElement(ElementName = "rn")] 
    public ushort runNum { get; set; } 

    [XmlElement(ElementName = "rt")] 
    public string routeName { get; set; } 

    [XmlElement(ElementName = "destSt")] 
    public ushort destStation { get; set; } 

    [XmlElement(ElementName = "destNm")] 
    public string destName { get; set; } 

    [XmlElement(ElementName = "trDr")] 
    public byte trainDir { get; set; } 

    [XmlElement(ElementName = "prdt")] 
    public string prdTime {get; set;} 

    [XmlElement(ElementName = "arrT")] 
    public string arrTime { get; set; } 

    [XmlElement(ElementName = "isApp")] 
    public ushort isApp { get; set; } 

    [XmlElement(ElementName = "isSch")] 
    public ushort isSch { get; set; } 

    [XmlElement(ElementName = "isDly")] 
    public ushort isDly { get; set; } 

    [XmlElement(ElementName = "isFlt")] 
    public ushort isFlt { get; set; } 

    [XmlElement(ElementName = "flags")] 
    public string flags { get; set; } 

    [XmlElement(ElementName = "lat")] 
    public double lat { get; set; } 

    [XmlElement(ElementName = "lon")] 
    public double lon { get; set; } 

    [XmlElement(ElementName = "heading")] 
    public ushort heading { get; set; } 
} 
+0

您在元素的trainingDataResult中缺少一个属性。否则,这个答案似乎是正确的。 –

+0

@RalphAllanRice确实如此,但在OP的来源中也没有。 – Xiaoy312

+0

感谢所有的回复。当我按照上面的方法更新模型时,我现在收到一个错误消息,说“不是我期望的。”我早些时候遇到了这个问题,并通过添加XmlRoot属性来解决它。 – orajestad9

0

我只知道如何反序列化从一个文件中的元素列表,但也许它可以帮助...

List<trainData> result = new List<trainData>; 
    using (FileStream stream = new FileStream(Filepath,Filemode.Open) 
{ 
XmlSerializer Serializer =new XmlSerializer(typeof(List<trainData>)); 
result = Serializer.Deserialize(stream); 
} 
+0

提供的xml甚至不包含任何类似数组的东西...... – Xiaoy312

0

如果是complexType,我认为它需要作为类来表示整个元素。创建第二个类(例如“ETAData”)以包含该元素下的元素。您还需要在trainData类中具有该类型的属性,并且还使用[XmlElementAttribute]标记该属性。

编辑:@ Xiaoy312答案更简洁,基本上说明了我所说的。