本文介绍了JSON.NET自定义序列化以排除属性名称的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用Json.NET,并且具有以下代码.

I am using Json.NET and I have the following code.

public class Row
{
    [JsonProperty]
    public IDictionary<string, object> Cells { get; set; }
}

行和单元格是动态生成的,我具有C#动态/扩展功能来创建这些单元格.当Json.NET序列化动态实例时,它将生成我想要的正确的json结构.但是,对于大型数据结构,它会对性能产生不利影响.例如,JsonSerializer在序列化期间相当广泛地调用DynamicObject TryGetMember.因此,我需要一个静态数据结构,因此序列化会更快. synamic Expando对象仍然可以创建动态属性,但是我希望Json.NET序列化使用静态结构(基于动态结构创建),以便序列化更快.

The rows and cells are dynamically generated and I had C# dynamic/Expando feature to create those Cells. When Json.NET serializes the dynamic instances, it produces the correct json structure I want. However for a large data structure it has an adverse effect on the performance. For example, JsonSerializer calls DynamicObject TryGetMember quite extensively during the serialization. Therefore I needed a static data structure so the serialization would be much quicker. The synamic Expando object would still create dynamic properties, but I wanted the Json.NET serialization to use the static structure (created based on the dynamic structure) so the serialization would be much quicker.

基于动态结构填充Cells字典,并通过调用JsonConvert生成序列化的json结构,如下所示.

Cells dictionary get populated based on the dynamic structure, and by invoking the JsonConvert, it produces the serialized json structure as below.

 string serializeObject =  JsonConvert.SerializeObject(data, Formatting.Indented);

//json输出:

 {

    "Data": [
              {
                "Cells": {
                     "column1": "20",
                     "column2": "20"
                     }
              },
              {
                "Cells": {
                    "column1": "20",
                    "column2": "20"
                    }
              }
      ]
}

但是我绑定到的UI Grid需要下面的json结构

However the UI Grid which I’m binding to, require the below json structure

   "Data": [
               {
                     "column1": "20",
                     "column2": "20"
               },
               {
                    "column1": "20",
                    "column2": "20"
               }
           ]

有没有办法删除单元"并生成上面的Json结构?

Is there a way I could remove the "Cells" and produce the Json structure as above?

我查看了JSON.NET帮助文档,但找不到实现此目的的方法.还尝试覆盖DynamicContractResolver的CreateProperty方法,以查看我是否可以更改序列化行为,但我无法这样做

I looked at the JSON.NET help docos and I could not find a way to achieve this.Also tried overriding the DynamicContractResolver’s CreateProperty method to see if I can change the serialization behaviour, but I was unable to do so

 public class DynamicContractResolver : DefaultContractResolver
 {
    protected override JsonProperty CreateProperty(System.Reflection.MemberInfo member, MemberSerialization memberSerialization)
    {
        if (member.Name == "Cells")
        {
             //remove the name "Cells" from the serialized structure
        }
        return base.CreateProperty(member, memberSerialization);
    }
 }

还是不仅仅支持这种方法?任何建议或指示,不胜感激.

Or this is not simply supported? Any suggestions or directions much appreciated.

推荐答案

找到了一种通过创建自定义转换器来解决此问题的方法.下面的代码产生我需要的Json结果.

Found a way to get around this by creating a custom converter. The below code produces the Json result I need.

public class GridJsonConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        return true; //TODO: more logic check the type before the conversion..
    }

    public override void WriteJson(JsonWriter writer,
       object value, JsonSerializer serializer)
    {
        var rows = (List<Row>)value;

        writer.WriteStartObject();
            writer.WritePropertyName("data");
                writer.WriteStartArray();

        foreach (var row in rows)
        {
            writer.WriteStartObject();
            var cells = row.Cells;

            foreach (var cell in cells)
            {
                writer.WritePropertyName(cell.Key);
                writer.WriteValue(cell.Value);
            }

            writer.WriteEndObject();
        }

        writer.Flush();
    }

    public override object ReadJson(JsonReader reader, Type objectType,
       object existingValue, JsonSerializer serializer)
    {
        throw new NotImplementedException();
    }
}

//用法示例:

  string serializeObject = JsonConvert.SerializeObject
 (someData, Formatting.Indented,   new GridJsonConverter());

这篇关于JSON.NET自定义序列化以排除属性名称的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-05 18:24