使用动态密钥将JSON反序列化为Object [英] Deserialize JSON with dynamic key into Object

查看:104
本文介绍了使用动态密钥将JSON反序列化为Object的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我知道已经对该主题提出了一些问题,但是我仍然很难理解.我有一个返回的相当复杂的JSON对象,它在开始时有一个动态键.我正在尝试将其反序列化为C#对象模型,但是我的问题是动态键:

I know there have been some questions already raised about this topic however I still struggle o understand it. I have quite a complex JSON object returning which has a dynamic key at the beginning. I am trying to deserialize it into a C# object model but my problem is the dynamic key:

{
"ISBN:0903393972": {
    "bib_key": "ISBN:0903393972",
    "details": {
        "publishers": ["Sweet & Maxwell"],
        "physical_format": "Hardcover",
        "title": "Tanker Voyage Charter Parties",
        "created": {
            "type": "/type/datetime",
            "value": "2008-04-30T09:38:13.731961"
        },
        "authors": [{
            "name": "F.M. Ventris",
            "key": "/authors/OL3610236A"
        }],
}}}

我的头痛来自动态的"ISBN:0903393972"部分.以下也是该模型的一部分:

My headache comes from the "ISBN:0903393972" part which is dynamic. Below is also part of the model:

[DataContract]
public class Created
{
    [DataMember]
    public string type { get; set; }
    [DataMember]
    public DateTime value { get; set; }
}

[DataContract]
public class Author
{
    [DataMember]
    public string name { get; set; }
    [DataMember]
    public string key { get; set; }
}

[DataContract]
public class Details
{
    [DataMember]
    public List<string> publishers { get; set; }
    [DataMember]
    public string physical_format { get; set; }
    [DataMember]
    public string title { get; set; }
    [DataMember]
    public Created created { get; set; }
    [DataMember]
    public List<Author> authors { get; set; }
}

[DataContract]
public class ISBN
{
    [DataMember]
    public string bib_key { get; set; }
    [DataMember]
    public Details details { get; set; }
}

[DataContract]
public class RootObject
{
    public Dictionary<string, ISBN> bookRoot { get; set; }
}

我正在使用以下代码反序列化JSON格式(在我将"ISBN:0903393972"硬编码为对象的键的情况下有效):

I am deserializing the JSON format with the below code (which works in case I hard code the "ISBN:0903393972" as the key of the object):

        string json = new WebClient().DownloadString(URLAddress);
        JObject book = JObject.Parse(json) as JObject;

        // Copy to a static Album instance
        RootObject deserializedBook = book.ToObject<RootObject>();

        return deserializedBook;

我确定我在这里遗漏了一些东西,但是他整天都在努力寻找解决方案.任何帮助将不胜感激!

I am sure that I'm missing something here but have been struggling he whole day already in trying to find a solution. Any help would be really appreciated!

推荐答案

您很亲密.

在JSON中,动态键位于根级别,因此该对象需要用Dictionary<string, ISBN>表示.看来您已经意识到这一点,但是,在您的模型中,您添加了一个外部类来包含字典.这与JSON不一致,在这里不需要.相反,您应该直接反序列化到字典中:

In your JSON, the dynamic keys are at the root level, and so that object needs to be represented by a Dictionary<string, ISBN>. It seems you have realized this, however, in your model, you have added an outer class to contain the dictionary. This doesn't line up with the JSON and is not needed here. Instead, you should deserialize directly into the dictionary:

string json = new WebClient().DownloadString(URLAddress);
var bookRoot = JsonConvert.DeserializeObject<Dictionary<string, ISBN>>(json);

从那里,您可以在字典上的Values集合上循环以访问图书,而无需事先知道键:

From there, you can loop over the Values collection on the dictionary to access the books without having to know the key(s) in advance:

foreach (var isbn in bookRoot.Values)
{
    // ...
}

或者,如果您只希望读一本书,则可以从字典中获取,如下所示:

Or, if you're expecting only one book, you can get it from the dictionary like this:

var isbn = bookRoot.Values.First();

这是一个有效的演示: https://dotnetfiddle.net/csgSKp

Here is a working demo: https://dotnetfiddle.net/csgSKp

这篇关于使用动态密钥将JSON反序列化为Object的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆