您可以使用简单的JsonConverter 来完成此操作。例如,如果我们让您的 Data 类成为支持任何对象值类型的泛型类,您会这样做:
public sealed class Root<T>
{
public Data<T> data { get; set; }
}
[JsonConverter(typeof(GenericDataResponseConverter))]
public sealed class Data<T>
{
public string Name { get; set; }
public T DataResponse { get; set; }
}
class GenericDataResponseConverter : JsonConverter
{
Type GetDataResponseType(Type objectType)
{
return (objectType.IsGenericType && objectType.GetGenericTypeDefinition() == typeof(Data<>) ? objectType.GetGenericArguments()[0] : null);
}
public override bool CanConvert(Type objectType)
{
return GetDataResponseType(objectType) != null;
}
object ReadJsonGeneric<T>(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
var data = ((Data<T>)existingValue) ?? new Data<T>();
var obj = JObject.Load(reader);
data.Name = (string)obj["name"];
data.DataResponse = obj[data.Name].ToObject<T>(serializer);
return data;
}
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
var method = GetType().GetMethod("ReadJsonGeneric", BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Public);
var genericMethod = method.MakeGenericMethod(new[] { GetDataResponseType(objectType ) });
return genericMethod.Invoke(this, new object[] { reader, objectType, existingValue, serializer });
}
void WriteJsonGeneric<T>(JsonWriter writer, object value, JsonSerializer serializer)
{
var data = (Data<T>)value;
var dict = new Dictionary<string, object>
{
{ "name", data.Name },
{ data.Name, data.DataResponse },
};
serializer.Serialize(writer, dict);
}
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
{
var method = GetType().GetMethod("WriteJsonGeneric", BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Public);
var genericMethod = method.MakeGenericMethod(new[] { GetDataResponseType(value.GetType()) });
genericMethod.Invoke(this, new object[] { writer, value, serializer });
}
}
然后,像这样使用它:
var root = JsonConvert.DeserializeObject<Root<DataResponse>>(jsonString);
Debug.WriteLine(JsonConvert.SerializeObject(root, Formatting.Indented));
如果您不需要通用的DataResponse 类型,它会变得更加容易:
public sealed class Root
{
public Data data { get; set; }
}
[JsonConverter(typeof(DataResponseConverter))]
public sealed class Data
{
public string Name { get; set; }
public DataResponse DataResponse { get; set; }
}
class DataResponseConverter : JsonConverter
{
public override bool CanConvert(Type objectType)
{
return objectType == typeof(Data);
}
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
var data = ((Data)existingValue) ?? new Data();
var obj = JObject.Load(reader);
data.Name = (string)obj["name"];
data.DataResponse = obj[data.Name].ToObject<DataResponse>(serializer);
return data;
}
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
{
var data = (Data)value;
var dict = new Dictionary<string, object>
{
{ "name", data.Name },
{ data.Name, data.DataResponse },
};
serializer.Serialize(writer, dict);
}
}