提问人:eek 提问时间:11/6/2023 最后编辑:dbceek 更新时间:11/6/2023 访问量:84
C# - 在循环访问动态 JSON 时遇到问题
C# - Having trouble iterating over a dynamic JSON
问:
我正在尝试从网站中提取 JSON 数据,但在迭代它返回的对象时遇到了一些麻烦。有人可以协助浏览这个结构吗?我对它不统一感到困惑。
using (var httpClient = new HttpClient())
{
httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", "myToken");
httpClient.BaseAddress = new Uri("https://app.website.com/data/");
HttpResponseMessage response = httpClient.GetAsync("getData.json?item=myItem").Result;
response.EnsureSuccessStatusCode();
dynamic result = JsonConvert.DeserializeObject(response.Content.ReadAsStringAsync().Result);
Console.WriteLine("Result: " + result);
dynamic jsonArray = result.results;
foreach (var item in jsonArray.items)
{
Console.WriteLine(item.date1);
}
}
我正在处理的 JSON 数组如下。我的目标是遍历并获取所有 和 值。我不需要别的。item
date1
date2
{
"results": {
"copyright": "Copyright",
"items": [{
"info": {
"longname": "XXX",
"shortname": "YYY"
},
"item": [{
"date1": "2022-01-01",
"date2": "2022-01-05",
}, {
"date1": "2022-04-01",
"date2": "2021-04-07",
}],
"key": {
"keyName": "AAA",
"keySym": "BBB",
},
"symString": "BBB"
}],
"count": 1
}
}
答:
2赞
dbc
11/6/2023
#1
通过使用 IntelliSense 以及编译时类型检查,你正在为自己做额外的工作。Json.NET for 返回的基础类型通常是 JToken
的某个子类型,因此完成任务的最简单方法是反序列化为 SelectTokens() 并使用 SelectTokens(),
如下所示:dynamic
dynamic
JToken
var result = JsonConvert.DeserializeObject<JToken>(jsonString);
var dates = result.SelectTokens("results.items[*].item[*]")
.Select(i => new { date1 = i["date1"].ToObject<DateOnly>(), date2 = i["date2"].ToObject<DateOnly>() });
foreach (var item in dates)
{
Console.WriteLine($"Date1={item.date1}, Date2={item.date2}.");
}
哪些打印
Date1=01/01/2022, Date2=01/05/2022.
Date1=04/01/2022, Date2=04/07/2021.
笔记:
传递给的查询字符串是一个 JSONPath 查询,其中包含用于选择数组和嵌套数组中的所有项的通配符。
"results.items[*].item[*]"
SelectTokens()
"items"
"item"
DateOnly
是在 .NET 6 中引入的。在早期版本中,请使用 .DateTime
使用有时会导致死锁,有关详细信息,请参阅导致死锁的 async/await 示例。如果发生这种情况,请考虑将代码转换为异步代码,或参阅同步使用 HttpClient 的“正确方法”是什么?。
httpClient.GetAsync(url).Result
在这里演示小提琴
评论
0赞
gunr2171
11/6/2023
和之间有什么区别吗?JsonConvert.DeserializeObject<JToken>(jsonString)
JToken.Parse(jsonString)
1赞
dbc
11/6/2023
@gunr2171 - 很少。 自动加载行信息,而不加载行信息,导致内存使用量略有增加。使用 时传递设置也更容易。但实际上我只是使用了,因为 OP 已经在使用它了。JToken.Parse(jsonString)
JsonConvert.DeserializeObject<JToken>(jsonString)
DeserializeObject()
DeserializeObject()
0赞
eek
11/6/2023
这效果很好!谢谢!
0赞
eek
11/6/2023
您将如何访问该物业?我试过了,但没有用keyName
key
results.items[*].key
评论
dynamic
JToken.Parse
dynamic
key