簡體   English   中英

使用JSON.NET反序列化任何內容

[英]Deserializing anything using JSON.NET

將JSON反序列化為已知類型或Dictionary對象沒有問題,但是如果我不知道輸入將是什么情況呢? 具體來說,我指的是接收一個JSON字符串,它表示一組鍵值對的平面或嵌套:

{ 
  foo: 'bar',
  baz: 42
}

要么

{
  foo: 
  {
    bar: 42,
    baz: ['foo', 'bar', 'baz']
  }
}

但是,如果輸入不是鍵值對,而是一個數組,或帶有其他嵌套對象(包括數組)的對象數組,情況又如何呢?

[
  { foo: 'bar', baz: [ 1, 2, 3 ] },
  { foo: 'baz', bar: [ 4, 5, 6 ] }
]

我的目標是擁有一個單一的類,可以將以上任何內容反序列化為一個類,然后迭代其每個成員。 輸入可以是任何結構,所以我不能假設數據會匹配我已經定義的任何類型。

我還沒有找到一種方法來做到這一點。 有人有指導嗎?

編輯:

看起來很容易JToken.Parse JSON字符串; 一個有用的下一步將是迭代其成員並分別處理JArray和JObject。

您正在描述的內容已經存在於Json.Net中-它是LINQ-to-JSON API (JTokens)。 下面是一個使用它解析任意JSON並遍歷成員的示例。 請注意,您需要使用遞歸方法,因為JSON可以嵌套到任何深度。

using Newtonsoft.Json.Linq;
public class Program
{
    public static void Main(string[] args)
    {
        string json1 = @"
        {
          ""foo"": { ""bar"": 42, ""baz"": [ ""a"", ""b"", ""c"" ] }
        }";
        DeserializeAndDump(json1, "example 1");

        string json2 = @"
        [
          { ""foo"": ""bar"", ""baz"": [ 1, 2, 3 ] },
          { ""foo"": ""baz"", ""bar"": [ 4, 5, 6 ] }
        ]";
        DeserializeAndDump(json2, "example 2");
    }

    public static void DeserializeAndDump(string json, string label)
    {
        Console.WriteLine("---- " + label + " ----");
        JToken token = JToken.Parse(json);
        DumpJToken(token);
        Console.WriteLine();
    }

    public static void DumpJToken(JToken token, string indent = "")
    {
        if (token.Type == JTokenType.Object)
        {
            Console.WriteLine(indent + "begin object");
            foreach (JProperty prop in token.Children<JProperty>())
            {
                Console.WriteLine(indent + "  " + prop.Name + ":");
                DumpJToken(prop.Value, indent + "    ");
            }
            Console.WriteLine(indent + "end object");
        }
        else if (token.Type == JTokenType.Array)
        {
            Console.WriteLine(indent + "begin array");
            foreach (JToken child in token.Children())
            {
                DumpJToken(child, indent + "  ");
            }
            Console.WriteLine(indent + "end array");
        }
        else
        {
            Console.WriteLine(indent + token.ToString() + " (" + token.Type.ToString() + ")");
        }
    }
}

這是上面的輸出:

---- example 1 ----
begin object
  foo:
    begin object
      bar:
        42 (Integer)
      baz:
        begin array
          a (String)
          b (String)
          c (String)
        end array
    end object
end object

---- example 2 ----
begin array
  begin object
    foo:
      bar (String)
    baz:
      begin array
        1 (Integer)
        2 (Integer)
        3 (Integer)
      end array
  end object
  begin object
    foo:
      baz (String)
    bar:
      begin array
        4 (Integer)
        5 (Integer)
        6 (Integer)
      end array
  end object
end array

小提琴: https : //dotnetfiddle.net/dfk0sj

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM