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

C#使用Newtonsoft.Json反序列化JSON时嵌套字典转换报错如何解决

问题原因

报错是因为JSON中的rights字段存储的是转义后的JSON字符串,不是标准的字典对象结构,Newtonsoft.Json默认不会自动对嵌套的JSON字符串执行二次反序列化。

最优实现方案:自定义JsonConverter

该方案侵入性低、可复用,不需要修改原有类的业务逻辑,一次定义可在所有同场景下使用。

第一步:定义自定义转换器

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

public class StringToDictionaryConverter : JsonConverter<Dictionary<int, long>>
{
    public override Dictionary<int, long> ReadJson(JsonReader reader, Type objectType, Dictionary<int, long> existingValue, bool hasExistingValue, JsonSerializer serializer)
    {
        // 读取到字符串时先执行二次反序列化
        if (reader.TokenType == JsonToken.String)
        {
            string jsonStr = reader.Value?.ToString();
            return string.IsNullOrEmpty(jsonStr) ? new Dictionary<int, long>() : JsonConvert.DeserializeObject<Dictionary<int, long>>(jsonStr);
        }
        // 本身是字典结构时走默认反序列化逻辑
        if (reader.TokenType == JsonToken.StartObject)
        {
            return serializer.Deserialize<Dictionary<int, long>>(reader);
        }
        return default;
    }

    public override void WriteJson(JsonWriter writer, Dictionary<int, long> value, JsonSerializer serializer)
    {
        // 序列化时如果需要转回字符串格式就启用下面的代码,不需要就走默认序列化逻辑
        // writer.WriteValue(JsonConvert.SerializeObject(value));
        serializer.Serialize(writer, value);
    }
}

第二步:绑定转换器到属性

在你的A类的rights属性上添加JsonConverter特性即可:

public class A
{
    public Guid userId { get; set; }
    public Guid businessId { get; set; }
    [JsonConverter(typeof(StringToDictionaryConverter))]
    public Dictionary<int, long> rights { get; set; }
}

配置完成后直接调用JsonConvert.DeserializeObject<A>(json)即可正常反序列化,不需要额外处理。

其他可选方案

如果不想新增转换器类,也可以通过属性中转实现:

public class A
{
    public Guid userId { get; set; }
    public Guid businessId { get; set; }
    [JsonProperty("rights")]
    public string RightsJson { get; set; }
    [JsonIgnore]
    public Dictionary<int, long> rights => string.IsNullOrEmpty(RightsJson) ? new Dictionary<int, long>() : JsonConvert.DeserializeObject<Dictionary<int, long>>(RightsJson);
}

该方案不需要额外定义转换器,但会在类中增加业务无关的中转属性,不如自定义转换器优雅。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.01 04:09:03