我有以下来自 API 的 JSON
{
"rates": {
"EURGBP": {
"rate": 0.871625,
"timestamp": 1619193484
},
"USDJPY": {
"rate": 107.939463,
"timestamp": 1619193484
}
}
}
我想创建类来反序列化这个 JSON。如果我进行 JSON 到 C# 的转换,我会得到以下 C# 类:
public class Rates
{
public EURGBP EURGBP { get; set; }
public USDJPY USDJPY { get; set; }
}
public class EURGBP
{
public double rate { get; set; }
public int timestamp { get; set; }
}
public class USDJPY
{
public double rate { get; set; }
public int timestamp { get; set; }
}
问题是可能会有更多对象进入
rates
对象。喜欢
"NZDUSD": {
"rate": 0.718962,
"timestamp": 1619198884
}
在这种情况下,我不会有一个类
NZDUSD
来反序列化新对象。
那么我是否可以有一个泛型类,使用它可以反序列化
rates
下的对象,因为它们将具有共同的属性?
或
我可以在反序列化期间或之后将
rates
下的对象转换为 List
或 Dictionary
吗?
您可以使用字典创建这样的对象模型:
public class Result
{
public IDictionary<string, Rate> Rates { get; set; }
}
public class Rate
{
public double rate { get; set; }
public int timestamp { get; set; }
}
然后使用Newtonsoft反序列化:
var values = Newtonsoft.Json.JsonConvert.DeserializeObject<Result>(json);
那么我是否可以有一个泛型类,使用它可以反序列化速率下的对象,因为它们将具有共同的属性?
有几种不同的方法可以实现此目的,Connell 已经提供了其中一种方法。另一种方法是创建您自己的
JsonConverter
。下面我将向您展示如何做到这一点。
-创建一个名为:
CurrencyConverter
的新类,确保它如下所示:
using System;
using System.Collections.Generic;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
public class CurrencyConverter : JsonConverter
{
public override bool CanConvert(Type objectType) => typeof(List<Rate>).IsAssignableFrom(objectType);
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
List<Rate> rates = new List<Rate>();
if (reader.TokenType == JsonToken.StartObject)
{
JToken token = JToken.Load(reader);
IEnumerable<JToken> tokenChildren = token.Root.First?.First?.Children();
foreach (JToken child in tokenChildren)
{
double dblRate = GetValue(child.First, "rate", 0d);
int intTimeStamp = GetValue(child.First, "timestamp", 0);
rates.Add(new Rate() { RateName = ((JProperty)child).Name, rate = dblRate, Timestamp = intTimeStamp });
}
}
return rates;
}
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
{
throw new NotImplementedException();
}
public T GetValue<T>(JToken jToken, string key, T defaultValue = default(T))
{
dynamic ret = jToken[key];
if (ret == null) return defaultValue;
if (ret is JObject) return JsonConvert.DeserializeObject<T>(ret.ToString());
return (T)ret;
}
}
-接下来创建一个名为
Rate
的新类:
public class Rate
{
public string RateName { get; set; }
public double rate { get; set; }
public int Timestamp { get; set; }
}
-最后反序列化你的
json
:
JsonSerializerSettings jsonSerializerSettings = new JsonSerializerSettings();
jsonSerializerSettings.Converters.Add(new CurrencyConverter());
var jsonOutput = JsonConvert.DeserializeObject<List<Rate>>(json, jsonSerializerSettings);
使用您提供的
json
,我得到了一个包含两个 Rate
对象的列表。