【问题标题】:How to convert Json array to list of objects in c#如何将Json数组转换为C#中的对象列表
【发布时间】:2013-10-25 05:33:27
【问题描述】:

我有如下的 Json 字符串

 {
"JsonValues":{

        "id": "MyID",

         "values": {
            "value1":{
                "id": "100",
                "diaplayName": "MyValue1"
            },
            "value2":{
                "id": "200",
                "diaplayName": "MyValue2"
            }
       }
}
}

我想将 Json 字符串转换为下面的类

  class ValueSet
   {
    [JsonProperty("id")]
    public string id
    {
        get;
        set;
    }
    [JsonProperty("values")]
    public List<Value> values
    {
        get;
        set;
    }
  }

class Value
{
    public string id
    {
        get;
        set;
    }
    public string DiaplayName
    {
        get;
        set;
    }
}

我的反序列化代码是

JavaScriptSerializer js = new JavaScriptSerializer();
        StreamReader sr = new StreamReader(@"ValueSetJsonString.txt");
        string jsonString = sr.ReadToEnd();
        var items = JsonConvert.DeserializeObject<ValueSet>(jsonString);

但是序列化后我得到空值,我该如何解决这个问题?

【问题讨论】:

标签: c# json json.net


【解决方案1】:

正如其他人已经指出的那样,您没有得到预期结果的原因是您的 JSON 与您尝试反序列化的类结构不匹配。您要么需要更改 JSON,要么更改您的类。由于其他人已经展示了如何更改 JSON,我将在此处采取相反的方法。

为了匹配您在问题中发布的 JSON,您的类应定义如下。请注意,我进行了以下更改:

  1. 我添加了一个Wrapper 类,对应于您的 JSON 中的外部对象。
  2. 我将ValueSet 类的Values 属性从List&lt;Value&gt; 更改为Dictionary&lt;string, Value&gt;,因为您的JSON 中的values 属性包含一个对象,而不是一个数组。
  3. 我添加了一些额外的 [JsonProperty] 属性来匹配 JSON 对象中的属性名称。

类定义:

class Wrapper
{
    [JsonProperty("JsonValues")]
    public ValueSet ValueSet { get; set; }
}

class ValueSet
{
    [JsonProperty("id")]
    public string Id { get; set; }
    [JsonProperty("values")]
    public Dictionary<string, Value> Values { get; set; }
}

class Value
{
    [JsonProperty("id")]
    public string Id { get; set; }
    [JsonProperty("diaplayName")]
    public string DisplayName { get; set; }
}

您需要反序列化为 Wrapper 类,而不是 ValueSet 类。然后您可以从Wrapper 获取ValueSet

var valueSet = JsonConvert.DeserializeObject<Wrapper>(jsonString).ValueSet;

这是一个演示的工作程序:

class Program
{
    static void Main(string[] args)
    {
        string jsonString = @"
        {
            ""JsonValues"": {
                ""id"": ""MyID"",
                ""values"": {
                    ""value1"": {
                        ""id"": ""100"",
                        ""diaplayName"": ""MyValue1""
                    },
                    ""value2"": {
                        ""id"": ""200"",
                        ""diaplayName"": ""MyValue2""
                    }
                }
            }
        }";

        var valueSet = JsonConvert.DeserializeObject<Wrapper>(jsonString).ValueSet;

        Console.WriteLine("id: " + valueSet.Id);
        foreach (KeyValuePair<string, Value> kvp in valueSet.Values)
        {
            Console.WriteLine(kvp.Key + " id: " + kvp.Value.Id);
            Console.WriteLine(kvp.Key + " name: " + kvp.Value.DisplayName);
        }
    }
}

这是输出:

id: MyID
value1 id: 100
value1 name: MyValue1
value2 id: 200
value2 name: MyValue2

【讨论】:

  • (jsonString).ValueSet;后缀为我做了!
【解决方案2】:

http://json2csharp.com/

我发现上面的链接非常有用,因为它通过从实际返回的 JSON 生成它们来纠正我的 C# 类。

然后我打电话给:

JsonConvert.DeserializeObject<RootObject>(jsonString); 

一切都按预期进行。

【讨论】:

  • 感谢该链接,希望我能在几周前看到它,因为它可以为我节省几天痛苦的工作!
  • 我一直在努力处理 JSON 字符串中的一个简单列表。您的链接为我解决了它。非常感谢!!!
  • app.QuickType.io 类似,但功能更多,广告更少。他们还有一个用于视觉工作室的插件。 (我与他们没有任何关系)
【解决方案3】:

您是否检查过这条线工作正常且您的字符串在其中有价值?

string jsonString = sr.ReadToEnd();

如果是,请在最后一行尝试此代码:

ValueSet items = JsonConvert.DeserializeObject&lt;ValueSet&gt;(jsonString);

或者如果你有一个 json 数组,你可以使用这样的列表:

List&lt;ValueSet&gt; items = JsonConvert.DeserializeObject&lt;List&lt;ValueSet&gt;&gt;(jsonString);

祝你好运

【讨论】:

    【解决方案4】:

    您的数据结构和您的 JSON 不匹配。

    你的 JSON 是这样的:

    {
        "JsonValues":{
            "id": "MyID",
            ...
        }
    }
    

    但是您尝试将其序列化为的数据结构是这样的:

    class ValueSet
    {
        [JsonProperty("id")]
        public string id
        {
            get;
            set;
        }
        ...
    }
    

    您正在跳过一个步骤:您的 JSON 是一个具有一个名为 JsonValues 的属性的类,该属性具有您的 ValueSet 数据结构的对象作为值。

    在你的班级里,你的 JSON 是这样的:

    "values": { ... }
    

    你的数据结构是这样的:

    [JsonProperty("values")]
    public List<Value> values
    {
        get;
        set;
    }
    

    请注意,JSON 中的{ .. } 定义了一个对象,而[ .. ] 定义了一个数组。因此,根据您的 JSON,您没有一堆值,但您有 one 值对象,其属性 value1value2 类型为 Value

    由于反序列化器需要一个数组,但获取的是一个对象,它会做它可以做的最不具破坏性(异常)的事情:跳过该值。您的属性values 保持其默认值:null

    如果可以:调整您的 JSON。以下内容将与您的数据结构相匹配,并且很可能是您真正想要的:

    {
        "id": "MyID",
    
         "values": [
             {
                "id": "100",
                "diaplayName": "MyValue1"
             }, {
                "id": "200",
                "diaplayName": "MyValue2"
             }
         ]
    }
    

    【讨论】:

    • 我改变了这样的 json 结构,但我仍然在对象中得到空值
    • 我忽略了这一点。请注意,在您的 C# 中您有 DiaplayName,但在您的 JSON 中您有 diaplayName。名称区分大小写。在 C# 中更改您的属性名称,JSON 或使用 JsonPropertyAttribute 告诉序列化程序您的属性的 JSON 名称。
    • 此外,最好在 StackOverflow 上更准确地描述您的错误描述。你得到null values in object - 究竟什么是空?你得到的整个对象?你的清单?单一属性?哪个物业?您越精确,人们就越容易为您提供帮助(甚至可能您自己也注意到了错误)。
    【解决方案5】:

    Json 转换为 C# 类 = https://json2csharp.com/json-to-csharp

    架构出来后

            WebClient client = new WebClient();
    
            client.Encoding = Encoding.UTF8;
    
            string myJSON = client.DownloadString("http://xxx/xx/xx.json");
    
            var valueSet = JsonConvert.DeserializeObject<Root>(myJSON);
    

    我们最大的一个错误是我们无法将类结构与json匹配。

    此连接将自动完成该过程。稍后您将对其进行编码;) = https://json2csharp.com/json-to-csharp

    就是这样。

    【讨论】:

    • 这个答案与 4 年前发布的 bultorious 的答案基本相同。操作已经有了 json,他们不需要使用旧 WebClient(我们现在有 HttpClientt)的代码的 sn-p 来检索它,其余的答案是“使用 json2csharp”,它已经发布了。请不要添加重复的答案
    【解决方案6】:

    你有一个不匹配的json字符串,如果你想转换成一个列表,试试这个

    {
        "id": "MyID",
    
         "values": [
            {
                "id": "100",
                "diaplayName": "MyValue1",
            },
            {
                "id": "200",
                "diaplayName": "MyValue2",
            }
       ]    
    }
    

    【讨论】:

    • 谢谢。我像这样更改了 json 字符串,但我仍然得到空值。
    【解决方案7】:

    这也是可能的:

    using System.Web.Helpers;
    var listOfObjectsResult = Json.Decode<List<DataType>>(JsonData);
    

    【讨论】:

      【解决方案8】:

      这需要 JsonElement 并将其反序列化为对象列表。

      List<object> draftInvoices = JsonConvert.DeserializeObject<List<object>>(jsonDrafts.ToString());
      

      示例:

      [HttpPost]
              [Route("CreateDraft")]
              public async Task<IActionResult> CreateDraft([FromBody] JsonElement jsonDrafts)
              {
                  List<object> draftInvoices = JsonConvert.DeserializeObject<List<object>>(jsonDrafts.ToString());
                   
                
                      for (int i = 0; i < draftInvoices.Count; i++) 
                       {
                        ........
                       }  
      

      【讨论】:

        【解决方案9】:

        您可以使用 Json.Net 框架来执行此操作。 就像这样:

        Account account = JsonConvert.DeserializeObject&lt;Account&gt;(json);

        首页:http://json.codeplex.com/

        有关此的文档:http://james.newtonking.com/json/help/index.html#

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-10-18
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-09-21
          相关资源
          最近更新 更多