【问题标题】:Deserialize a Json containing a list of object反序列化包含对象列表的 Json
【发布时间】:2015-09-16 13:36:57
【问题描述】:

我在一个 UniversalApp 上工作,它调用许多返回 JSON 数据的 Web 服务。

所有的网络服务都返回给我一个包含这个结构的第一级 Json (WsResponse.cs):

public string status { get; set; }
public object data { get; set; }
public List<object> errors { get; set; }

如果状态为“success”,我可以通过以下方式反序列化简单数据对象:

WsResponse wsResponse = JsonConvert.DeserializeObject<WsResponse>(response);    
User user = JsonConvert.DeserializeObject<User>(wsResponse.data.ToString());

在其他情况下,需要先在结果对象中反序列化,然后再反序列化数据:

WsResponse wsResponse = JsonConvert.DeserializeObject<WsResponse>(response);
WsResponseResult wsResponseResult = JsonConvert.DeserializeObject<WsResponseResult>(
                                                            wsResponse.data.ToString());
List<Theme> themes = JsonConvert.DeserializeObject<List<Theme>>(
                                                    wsResponseResult.result.ToString());

但如果状态是“failure”,我需要捕获错误列表。但我无法反序列化这个对象列表...... 以下是我从 web 服务中获取的包含错误的 JSON 数据示例:

{
  "status": "failure",
  "data": {},
  "errors": [
    {
      "200": "The parameter 'email' is not present"
    },
    {
      "200": "The parameter 'password' is not present"
    }
  ]
}

我尝试通过以下方式反序列化它:

List<KeyValuePair<string, string>> kvpError = new List<KeyValuePair<string,string>>();
kvpError = JsonConvert.DeserializeObject<List<KeyValuePair<<string, string>>>(
                                                            wsResponse.errors.ToString());

Dictionary<string, string> dError = new Dictionary<string, string>();
dError = JsonConvert.DeserializeObject<Dictionary<string, string>>(
                                                            wsResponse.errors.ToString());

=> 但它不起作用

我还尝试在反序列化之前检查错误数据:

foreach(var error in wsResponse.errors)
{                        
    KeyValuePair<string, string> kvpError = new KeyValuePair<string,string>();
    kvpError = JsonConvert.DeserializeObject<KeyValuePair<string, string>>(
                                                                        error.ToString());
}

=> 但效果并不好...

您对如何解决我的问题有想法吗?

【问题讨论】:

    标签: c# json web-services serialization json.net


    【解决方案1】:

    您的 JSON 的结构方式,errors 实际上是 List&lt;Dictionary&lt;string, string&gt;&gt;。如果您使用它而不是 List&lt;object&gt;,它将正确反序列化错误:

    public class Response
    {
        public string status { get; set; }
        public object data { get; set; }
        public List<Dictionary<string, string>> errors { get; set; }
    }
    

    产量:

    旁注 - 如果您对 JSON 结构有任何控制权,最好使用一个可以反序列化的 List&lt;KeyValuePair&lt;string, string&gt;&gt;。此外,实际上不是使用object data,而是在JSON 中传递User 属性,这样您就可以避免双重反序列化。

    如果您希望将其反序列化为 List&lt;KeyValuePair&lt;string, string&gt;&gt;,您的 JSON 需要如下所示:

    {
      "status": "failure",
      "data": {},
      "errors": [
        {
          "Key": "200", "Value": "The parameter 'email' is not present"
        },
        {
          "Key": "200", "Value": "The parameter 'password' is not present"
        }
      ]
    }
    

    【讨论】:

    • 谢谢,它工作正常。但是 JSON 的这种结构不是很好,因为每个字典只会包含一项...
    • @Gold.strike - 我同意,这就是我在回答的底部 pqrt 中所说的。如果可能,请考虑重构您的 JSON。
    • 我将与我的客户讨论这个问题,看看我们是否可以更改 JSON 结构。你用什么工具来查找对象的类型?
    • @Gold.strike 我没有使用工具,我只是对 JSON 和序列化有经验,所以我知道这是问题所在。
    猜你喜欢
    • 1970-01-01
    • 2016-09-27
    • 2016-10-01
    • 1970-01-01
    • 2015-06-11
    • 1970-01-01
    • 1970-01-01
    • 2012-09-06
    • 2017-07-21
    相关资源
    最近更新 更多