You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Json.NET自定义类为键的字典如何实现预期键值序列化格式

解决方案

问题原因

你当前使用的转换器逻辑是将字典转换为List<KeyValuePair<TKey, TValue>>进行序列化,Json.NET默认会将KeyValuePair类型序列化为包含Key和Value两个属性的对象,这就是你当前得到不符合预期格式的原因。

调整后的转换器实现

using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System.Collections.Generic;
using System.Linq;

public class CustomDictionaryConverter<TKey, TValue> : JsonConverter
{
    public override bool CanConvert(Type objectType) => objectType == typeof(Dictionary<TKey, TValue>);

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        var dict = (Dictionary<TKey, TValue>)value;
        writer.WriteStartObject();
        
        foreach (var kv in dict)
        {
            // 利用已注册的转换器序列化键,提取为字符串形式的属性名
            var keyToken = JToken.FromObject(kv.Key, serializer);
            string propertyName = keyToken.Type == JTokenType.String 
                ? keyToken.Value<string>() 
                : keyToken.ToString();
            
            writer.WritePropertyName(propertyName);
            // 序列化值,自动复用对应转换器
            serializer.Serialize(writer, kv.Value);
        }
        
        writer.WriteEndObject();
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        var resultDict = new Dictionary<TKey, TValue>();
        var jsonObj = JObject.Load(reader);
        
        foreach (var property in jsonObj.Properties())
        {
            // 将属性名反序列化为自定义键类型
            TKey key = JsonConvert.DeserializeObject<TKey>(JsonConvert.ToString(property.Name), serializer.Converters.ToArray());
            // 将属性值反序列化为自定义值类型
            TValue value = property.Value.ToObject<TValue>(serializer);
            
            resultDict.Add(key, value);
        }

        return resultDict;
    }
}

注意事项

  • 你已经实现的TKey专属JsonConverter需要支持从字符串反序列化、以及序列化输出为合法的JSON属性名字符串,否则会出现格式错误
  • 该实现会自动复用你为TKey、TValue注册的专属序列化/反序列化逻辑,无需额外适配
  • 如需处理空字典、null值等特殊场景,可以在遍历逻辑前增加对应判空分支

内容的提问来源于stack exchange,提问作者Vic

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.07 13:51:02