Json.net C#序列化/反序列化多个(不同类型)对象

时间:2017-01-17 12:36:22

标签: c# json object serialization json.net

我正在使用来自newtonsoft的Json.net。

目前,我正在学习数据库存储的替代方案。 我有两天遇到以下问题:

我想以JSON格式保存本地数据。 我有以下(xml)结构:

<? xml version="1.0"?>
<data>
    <transactions>
        <transaction>
            <id>1</id>
            <type>1</type>
            <name>a name</name>
            <datetime>01-01-2017 00:00</datetime>
            <amount>34,05</amount>
        </transaction>
        <transaction>
            <id>2</id>
            <type>type2</type>
            <name>test transaction 2</name>
            <datetime>01-02-2017 00:00</datetime>
            <amount>23,03</amount>
        </transaction>
    </transactions>
    <categories>
        <category>
            <id>1</id>
            <name>cat 1</name>
            <description>a desc for cat 1</description>
            <color>red</color>
            <subcategories>
                <subcategory>
                    <id>1</id>
                    <name>subcat 1</name>
                    <description>a desc for subcat 1</description>
                    <color>blue</color>
                </subcategory>
                <subcategory>
                    <id>2</id>
                    <name>subcat 2</name>
                    <description>a desc for subcat 2</description>
                    <color>yellow</color>
                </subcategory>
            </subcategories>
        </category>
        <category>
            <id>2</id>
            <name>cat 2</name>
            <description>a desc for cat 1</description>
            <color>red</color>
        </category>
    </categories>
</data>

当我将以下内容转换为JSON结构时:

 {
  "data": {
    "transactions": {
      "transaction": [
        {
          "id": "1",
          "type": "1",
          "name": "a name",
          "datetime": "01-01-2017 00:00",
          "amount": "34,05"
        },
        {
          "id": "2",
          "type": "type2",
          "name": "test transaction 2",
          "datetime": "01-02-2017 00:00",
          "amount": "23,03"
        }
      ]
    },
    "categories": {
      "category": [
        {
          "id": "1",
          "name": "cat 1",
          "description": "a desc for cat 1",
          "color": "red",
          "subcategories": {
            "subcategory": [
              {
                "id": "1",
                "name": "subcat 1",
                "description": "a desc for subcat 1",
                "color": "blue"
              },
              {
                "id": "2",
                "name": "subcat 2",
                "description": "a desc for subcat 2",
                "color": "yellow"
              }
            ]
          }
        },
        {
          "id": "2",
          "name": "cat 2",
          "description": "a desc for cat 1",
          "color": "red"
        }
      ]
    }
  }
}

我目前遇到的问题是我可以读取/写入json文件(使用JSON.NET) 但我只能写下一个(C#)对象。如果我尝试将我的子类别添加到我的类别中,我会得到奇怪的结果:

代码:

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace jsontest
{
    public partial class MainForm : Form
    {
        public MainForm()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            List<Category> Categorylist = new List<Category>();
            Category c;
            SubCategory sc;
            for (int i = 0; i < 5; i++)
            {
                // New category
                c = new Category
                {
                    id = i,
                    name = "Category " + i,
                    description = "Category description " + i,
                    color = Color.Red                  
                };

                //Creating a few sub categories
                if (i == 2 || i == 4)
                {
                    for (int j = 0; j < i; j++)
                    {
                        sc = new SubCategory
                        {
                            id = j,
                            name = "SubCategory " + j + "From Category with Id " + i,
                            description = "Subcategory description " + j + "from Category with Id " + i,
                            color = Color.Yellow
                        };
                        // Add subcategorie to category 
                        c.subcategories.Add(sc);
                    }
                }
                // Add to list
                Categorylist.Add(c);
            }

            string json = JsonConvert.SerializeObject(Categorylist, Newtonsoft.Json.Formatting.Indented);
            richTextBox1.AppendText(Environment.NewLine + json);
        }
    }

    public class Category
    {
        public int id { get; set; }
        public string name { get; set; }
        public string description { get; set; }
        public Color color { get; set; }
        public List<SubCategory> subcategories = new List<SubCategory>();
    }

    public class SubCategory
    {
        public int id { get; set; }
        public string name { get; set; }
        public string description { get; set; }
        public Color color { get; set; }
    }



}

结果:

[
  {
    "subcategories": [],
    "id": 0,
    "name": "Category 0",
    "description": "Category description 0",
    "color": "Red"
  },
  {
    "subcategories": [],
    "id": 1,
    "name": "Category 1",
    "description": "Category description 1",
    "color": "Red"
  },
  {
    "subcategories": [
      {
        "id": 0,
        "name": "SubCategory 0From Category with Id 2",
        "description": "Subcategory description 0from Category with Id 2",
        "color": "Yellow"
      },
      {
        "id": 1,
        "name": "SubCategory 1From Category with Id 2",
        "description": "Subcategory description 1from Category with Id 2",
        "color": "Yellow"
      }
    ],
    "id": 2,
    "name": "Category 2",
    "description": "Category description 2",
    "color": "Red"
  },
  {
    "subcategories": [],
    "id": 3,
    "name": "Category 3",
    "description": "Category description 3",
    "color": "Red"
  },
  {
    "subcategories": [
      {
        "id": 0,
        "name": "SubCategory 0From Category with Id 4",
        "description": "Subcategory description 0from Category with Id 4",
        "color": "Yellow"
      },
      {
        "id": 1,
        "name": "SubCategory 1From Category with Id 4",
        "description": "Subcategory description 1from Category with Id 4",
        "color": "Yellow"
      },
      {
        "id": 2,
        "name": "SubCategory 2From Category with Id 4",
        "description": "Subcategory description 2from Category with Id 4",
        "color": "Yellow"
      },
      {
        "id": 3,
        "name": "SubCategory 3From Category with Id 4",
        "description": "Subcategory description 3from Category with Id 4",
        "color": "Yellow"
      }
    ],
    "id": 4,
    "name": "Category 4",
    "description": "Category description 4",
    "color": "Red"
  }
]

有人可以帮助我走上正轨吗?

2 个答案:

答案 0 :(得分:0)

问题不在于c#代码。它按照你的指示产生输出。问题是从xml转换为JSON。转换后的JSON subcategories不是subcategory的数组,但其对象具有属性&#34;子类别&#34;和子类别是&#34;数组&#34;匿名类型的对象。 因此,如果您希望c#程序生成json结构,它看起来像是从xml转换为json,那么您需要更改Category类的定义,其中&#34;子类别&#34; property不是列表类型,而是另一个复杂类型,其属性名为&#34; subcategory&#34;反过来&#34;子类别&#34;将是匿名类型的数组/列表。

答案 1 :(得分:0)

如果我正确理解了这个问题,你想在添加JSON字符串之后保留其格式,与第一个相同。为此,您需要创建与JSON相对应的类。您可以使用this然后将JSON字符串反序列化为RootObject类的对象,并可以轻松添加TransactionsCategories。以下是添加新类别的示例(添加Transactions几乎相同):

var test = JsonConvert.DeserializeObject<RootObject>(json);
test.data.categories.category.Add(new Category() 
{
    id = "newId",
    name = "newName",
    color = "newColor",
    description = "new description",
    subcategories = new Subcategories() 
    { 
        subcategory = new List<Subcategory>() 
    }
});

test的序列化为您提供了新的JSON字符串。