【问题标题】:How to parse JSON object with another object childen with C#如何使用 C# 解析带有另一个子对象的 JSON 对象
【发布时间】:2016-08-03 20:34:05
【问题描述】:

我需要属性对象的属性名称:

这是我的代码:

JSON 示例:

 {
"dados":      [{"codigo_localidade":"1",
"localidade":"Adamantina",
"nome_localidade_pai":"Regi\u00e3o de Governo de Adamantina",
"codigo_variavel":"2",
"variavel":"Cr\u00e9dito Rural Agricultura",
"unidade":"(Em reais de 2015)",
"periodo":"1985\/1989-2011",
"ano":{"2010":"194.140.750"}
}

我的 C# 代码来解析我的 JSON:

  var resultObjects = AllChildren(JObject.Parse(cidadesSON))
                     .First(c => c.Type == JTokenType.Array && c.Path.Contains("dados"))
                     .Children<JObject>();

                    List<Cidade> cidades = new List<Cidade>();
                    Cidade item;
//fetch my array 
                    foreach (JObject result in resultObjects)
                    {
                        item = new Cidade();
                        item.localidade =(string)result["localidade"];
                        item.nome_localidad_pai =    (string)result["nome_localidade_pai"];
                        item.populacao = (string)result["ano"]["2010"];

                        //my problem
                        item.ano = ((JObject)result.["ano"]).Property("2010").Name;

                     cidades.Add(item);

                    }



                    grvCandidatos.DataSource = cidades;
                    grvCandidatos.CssClass = "table table-hover ";
                    grvCandidatos.DataBind();

这是获取对象的方法

private static IEnumerable<JToken> AllChildren(JToken json)
        {
            foreach (var c in json.Children())
            {
                yield return c;
                foreach (var cc in AllChildren(c))
                {
                    yield return cc;
                }
            }
        }

如有必要,这是我的模型类:

public class Cidade
        {
            public string localidade { get; set; }
            public string populacao { get; set; }
            public string nome_localidad_pai { get; set; }
            public string ano { get; set; }

        }

如果有人可以提供帮助,我将非常感激。

(对不起我的英语。)

【问题讨论】:

  • 你发布的Json无效jsonlint.com
  • cidadesSON的类型是什么?
  • 不清楚你想要什么。您可以在 pt.stackoverflow.com 发布您的问题,这是 StackOverflow 的葡萄牙语版本。 (我知道这一点是因为我会说葡萄牙语并且我看到了你的变量 :) 或者尝试更好地解释。
  • cidadesSON 是一个字符串变量 .... JSON 是正确的,因为我可以访问其他属性...我只是忘记关闭 'dados' 数组的 ']' 字符..跨度>
  • 在英语中找到答案要好得多......

标签: c# arrays json getjson


【解决方案1】:

TL;DR

您的代码的问题是我们不知道ano 属性的类型。您可以将该属性映射到 Dictionary&lt;string,object&gt;,并通过访问 Dictionary 的 Key 属性来获取实际的 ano。 请参阅下面的示例,了解如何执行此操作:

假设您可以在程序中使用 3rd 方库,您几乎可以通过在项目中添加 Json.Net 来减少所有代码:

“墙裙”类

public class Dado
{
    public string localidade { get; set; }
    public string populacao { get; set; }
    public string nome_localidad_pai { get; set; }

    [JsonConverter(typeof(AnoConverter))]
    public string ano { get; set; }
}

“根”类

public class RootObject
{
    public List<Dado> dados { get; set; }
}

然后,您可以创建自定义 JsonConverter 来操作 json 的反序列化:

public class AnoConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        throw new NotImplementedException();
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        //This deserialize the Ano into a Dictionary,
        //and returns the Key that contains the actual Year you want

        var ano  = serializer.Deserialize<Dictionary<string, object>>(reader);

        //I'm assuming that there will be always one year here.
        return ano.FirstOrDefault().Key;
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        throw new NotImplementedException();
    }
}

现在在您的程序中,只需执行以下操作即可将您的 json 反序列化为您的强类型类:

//Just reading the json from a file, nothing new here...
string json = String.Empty;
using (StreamReader r = new StreamReader("example.json"))
{
    json = r.ReadToEnd();
}

//Deserialize in json into a "RootObject"
var list = JsonConvert.DeserializeObject<RootObject>(json);

这将为您提供如下结果:

注意 您可以执行相同的过程来为您的 populacao 字段创建自定义 JsonConverter,但不是访问密钥,而是访问值。同样的逻辑。我不是特意做的,大家可以自己动手学习一下:)

【讨论】:

  • 这对我有用,但我发布了 Dado 类属性的名称必须与 Json 属性相同,你知道如何更改吗?有一个问题,因为populacao 它不是一个有效的属性名称。
  • 顺便谢谢您回答问题
  • 是的,它必须马赫。但是,您可以使用 JsonProperty 属性来装饰属性并为其指定自定义名称。在这里查看答案:stackoverflow.com/questions/8796618/…。我不明白你说的populacao问题。对我来说看起来不错..
【解决方案2】:

使用以下方法从 NSData 解析 JSON

   func parseJSON(data: NSData) -> ([String : AnyObject]?, NSError?) {

        var parsingError: NSError? = nil
        let parsedResult: [String : AnyObject]?
        do {

            parsedResult = try NSJSONSerialization.JSONObjectWithData(data, options: NSJSONReadingOptions.AllowFragments) as? [String : AnyObject]
        } catch let error as NSError {

            parsingError = error
            parsedResult = nil
        }
        return (parsedResult, parsingError)
    }

如果您在 NSData 中没有 JSON 使用以下函数将 JSON 转换为 NSData:

func jsonToNSData(json: AnyObject) -> NSData?{
    do {
        return try NSJSONSerialization.dataWithJSONObject(json, options: NSJSONWritingOptions.PrettyPrinted)
    } catch let myJSONError {
        print(myJSONError)
    }
    return nil;
}

【讨论】:

    猜你喜欢
    • 2019-05-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-06-10
    • 1970-01-01
    • 2016-01-21
    • 1970-01-01
    • 2017-08-20
    相关资源
    最近更新 更多