【问题标题】:How to read sections of JSON document?如何阅读 JSON 文档的各个部分?
【发布时间】:2019-10-16 18:19:33
【问题描述】:

我有一个 JSON 文档,我想访问 STATUS SECTION 的详细信息,但它一直返回 null。

JSON数据如图:

{ 
   "results":[ 
      { 
         "messageId":"15712480583306574",
         "to":"",
         "from":"TestServer",
         "sentAt":"2019-10-16T17:47:38.368+0000",
         "doneAt":"2019-10-16T17:47:38.370+0000",
         "smsCount":1,
         "mccMnc":"null",
         "price":{ 
            "pricePerMessage":0.0,
            "currency":"USD"
         },
         "status":{ 
            "groupId":5,
            "groupName":"REJECTED",
            "id":8,
            "name":"REJECTED_PREFIX_MISSING",
            "description":"Number prefix missing"
         },
         "error":{ 
            "groupId":0,
            "groupName":"OK",
            "id":0,
            "name":"NO_ERROR",
            "description":"No Error",
            "permanent":false
         }
      }
   ]
}

C#代码是:

string JsonData = response.Content.ToString();
dynamic results = JsonConvert.DeserializeObject<dynamic>(JsonData);
var statuses = results.status;
foreach(var stat in statuses) {
  string groupname = stat.groupName.Value;
  string name = stat.name.Value;
  string description = stat.description.Value;

}

它一直返回null,我怎样才能访问这些成员?我正在使用 Newtonsoft。

【问题讨论】:

  • 首先,status 是一个对象,而不是一个集合,您为什么希望能够迭代它?
  • 您可能需要考虑使用LINQ to JSON 而不是反序列化为dynamic...
  • @maccettura results.status 根据检查返回空值,所以迭代与否,它只是不断返回空值
  • @KevoyWalters 我希望我的评论能给你一个“啊哈”的时刻......如果results 是你的 json 集合属性,你希望你的 C# results.status 给你什么? Heretic Monkey 是对的,如果你反序列化为一个具体的类,你的问题会更加明显(因为如果你使用具体的对象,你现在正在做的事情不会编译)

标签: c# json json.net


【解决方案1】:

如果要访问状态对象属性,则需要重写整个代码。

string JsonData = response.Content.ToString();
var input = JObject.Parse(str);

var results = input["results"].Children();
var status = results.First()["status"];
string groupname = status["groupName"].ToString();
string name = status["name"].ToString();
string description = status["description"].ToString();

Console.WriteLine(groupname);
Console.WriteLine(name);
Console.WriteLine(description);

控制台中的结果

拒绝

REJECTED_PREFIX_MISSING

缺少数字前缀

但我宁愿使用具体类。您需要创建多个类。 Here 就是一个很好的例子。

public class Envelope
{
    public List<Item> Results { get; set; }
}

public class Item
{
    public Status Status { get; set; }
}

public class Status
{
    public int GroupId { get; set; }
    public string GroupName { get; set; }
    public int Id { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
}

之后使用就简单多了。

string JsonData = response.Content.ToString();
MyEnvelope envelope = JsonConvert.DeserializeObject<MyEnvelope>(JsonData);
var status = envelope.results[0].status;
Console.WriteLine(status.GroupName);
Console.WriteLine(status.Name);
Console.WriteLine(status.Description);

【讨论】:

    【解决方案2】:

    最佳选择:为 JSON 创建模型。

    public class Price
    {
        public double pricePerMessage { get; set; }
        public string currency { get; set; }
    }
    
    public class Status
    {
        public int groupId { get; set; }
        public string groupName { get; set; }
        public int id { get; set; }
        public string name { get; set; }
        public string description { get; set; }
    }
    
    public class Error
    {
        public int groupId { get; set; }
        public string groupName { get; set; }
        public int id { get; set; }
        public string name { get; set; }
        public string description { get; set; }
        public bool permanent { get; set; }
    }
    
    public class Result
    {
        public string messageId { get; set; }
        public string to { get; set; }
        public string from { get; set; }
        public DateTime sentAt { get; set; }
        public DateTime doneAt { get; set; }
        public int smsCount { get; set; }
        public string mccMnc { get; set; }
        public Price price { get; set; }
        public Status status { get; set; }
        public Error error { get; set; }
    }
    
    public class RootObject
    {
        public List<Result> results { get; set; }
    }
    

    那就RootObject results = JsonConvert.DeserializeObject&lt;RootObject&gt;(JsonData);

    公平选择:获取您想要的确切 JToken。

    using System;
    using Newtonsoft.Json;
    using Newtonsoft.Json.Serialization;
    using Newtonsoft.Json.Linq;
    
    public class Program
    {
        public static void Main()
        {
            string jsonData = "{\"results\":[{\"messageId\":\"15712480583306574\",\"to\":\"\",\"from\":\"TestServer\",\"sentAt\":\"2019-10-16T17:47:38.368+0000\",\"doneAt\":\"2019-10-16T17:47:38.370+0000\",\"smsCount\":1,\"mccMnc\":\"null\",\"price\":{\"pricePerMessage\":0.0,\"currency\":\"USD\"},\"status\":{\"groupId\":5,\"groupName\":\"REJECTED\",\"id\":8,\"name\":\"REJECTED_PREFIX_MISSING\",\"description\":\"Number prefix missing\"},\"error\":{\"groupId\":0,\"groupName\":\"OK\",\"id\":0,\"name\":\"NO_ERROR\",\"description\":\"No Error\",\"permanent\":false}}]}";
            JObject jObject = JObject.Parse(jsonData);
    
            Console.WriteLine(jObject.SelectToken("results[0].status"));
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-13
      • 1970-01-01
      • 2013-12-24
      • 2011-01-08
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多