我正在访问一个返回一些JSON的API,如下所示:
{"stats":{"X":{"Name":"X","Found":"Yes"}},"response":"OK","runtimeMs":798}
我想为它生成 C# 类,我使用了 json2sharp,它生成了诸如根对象的类,我修改如下:
public class RootObject
{
public Stats stats { get; set; }
public string response { get; set; }
public int runtimeMs { get; set; }
}
public class Stats
{
public string name { get; set; }
}
public class Variant
{
public string name { get; set; }
public string Found { get; set; }
}
我面临的问题是,在类统计中,我使用了名称,因为 json 会回复任何名称,例如 X 或 Y 或 Z。
我能够将 JSON 反序列化为根对象,但无法将任何数据放入统计类中。
JsonConvert.DeserializeObject<RootObject>(response.Content);
知道为什么我可能做错了吗?
您的问题与此类似 如何解析会导致非法 C# 标识符的 JSON 字符串?
因此,您的模型应该是
public class Variant
{
public string Name { get; set; }
public string Found { get; set; }
}
public class RootObject
{
public Dictionary<string, Variant> stats { get; set; }
public string response { get; set; }
public int runtimeMs { get; set; }
}
编辑
@evanmcdonnal如果使用 EZI 答案中显示的字典或带有名为 X、Y 和 Z 的字段的对象,则必须到处执行 nullity 或 keyexists 检查才能安全地使用该对象。
我不认为这个简单的linq很难写
rootObj.stats.Values.Where(....);
或
rootObj.stats.Keys.Select(....);
是因为 json.NET 正在类中查找与 JSON 中的字段名称匹配的属性名称。由于name
与 json 中的任何内容都不相似,因此它什么也找不到。
有两种方法可以解决此问题。您可以使用批注来说明要放置的 json 字段是什么,也可以更改属性的名称。但是,从您的帖子中听起来您是在说 json 中可能有一个名为 X
的对象或一个名为 Y
的对象,这两个选项都不会在所有情况下正确反序列化。我将编辑一些关于您可能想要如何处理它的想法。
根据OP的评论,这是您要查找的内容;
public class RootObject
{
public Stats stats { get; set; }
public string response { get; set; }
public int runtimeMs { get; set; }
}
public class Stats
{
public Varient X { get; set; }
public Varient Y { get; set; }
public Varient Z { get; set; }
}
public class Variant
{
public string name { get; set; }
public string Found { get; set; }
}
在代码的其他地方,您只需要有两个代码路径或进行转换,以避免到处执行无效性检查。
if (myInstance.X != null)
// it was X that was in the json
else if (myInstace.Y != null)
// it was Y
else
// not sure what happened, perhaps neither X nor Y were present.
现在,另一种选择是使其只是一个中介,然后定义另一个类型,该类型只有一个名为 name 的属性,并为其提供一个构造函数,该构造函数采用RootObject
并将任何不为 null 的值分配给它name
属性或任何您想要调用它的内容。我自己可能会做这样的事情,因为如果使用 EZI 答案中显示的字典或带有名为 X、Y 和 Z 的字段的对象,您必须到处执行 nullity 或 keyexists 检查才能安全地使用该对象。