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

C#中反序列化含动态属性名的Newtonsoft JSON数据

解决动态键JSON到C#对象的反序列化问题

你的问题核心在于JSON响应里的result字段是一个带有动态键(RITM编号)的对象,而你的C#模型里result直接定义为RITMDetails类型,两者结构不匹配,导致常规反序列化无法生效。下面给你两种简单可行的解决方案:

方案一:修改模型使用字典处理动态键

这是最直接的方法,只需要把result的类型从RITMDetails改成Dictionary<string, RITMDetails>,让字典来容纳那个动态的RITM编号键:

public class RITMGETRequestResponse
{
    // 用字典接收动态键值对
    public Dictionary<string, RITMDetails> result { get; set; }

    public class RITMDetails
    {
        public string business_justification { get; set; }
        public string number { get; set; }
        public string requested_for { get; set; }
        public string stage { get; set; }
        public string state { get; set; }
        public string Sys_ID { get; set; }
        public string var_name_arr { get; set; }
        public string Contoso_business_justification { get; set; }
        public string Contoso_catalog_item_footer { get; set; }
        public string Contoso_requested_for { get; set; }
        public string Contoso_sc_Appname { get; set; }
        public string Contoso_Sc_Contactinfo { get; set; }
        public string Contoso_sc_Description { get; set; }
        public string Contoso_sc_Purposeofthef5request { get; set; }
        public string Contoso_special_instructions { get; set; }
    }
}

然后用JSON序列化库完成反序列化,再提取字典里的唯一值(看起来你的JSON里result下只有一个RITM条目):

使用Newtonsoft.Json的代码:

string jsonResponse = @"{""result"": { ""RITM2572913"": { ""number"": ""RITM2572913"", ""state"": ""1"", ... } }}"; // 你的完整JSON字符串
var response = JsonConvert.DeserializeObject<RITMGETRequestResponse>(jsonResponse);

// 获取RITM详情对象
var ritmDetails = response.result.Values.FirstOrDefault();
if (ritmDetails != null)
{
    string sysId = ritmDetails.Sys_ID;
    string number = ritmDetails.number;
    // 其他属性都可以直接访问
}

使用System.Text.Json的代码:

using System.Text.Json;

var options = new JsonSerializerOptions 
{ 
    PropertyNameCaseInsensitive = true, // 忽略大小写匹配属性
    WriteIndented = true 
};
var response = JsonSerializer.Deserialize<RITMGETRequestResponse>(jsonResponse, options);

var ritmDetails = response.result.Values.FirstOrDefault();
if (ritmDetails != null)
{
    // 访问所需属性
}

方案二:不修改模型,先反序列化到动态对象再映射

如果你不想修改原有的模型结构,可以先把JSON反序列化为动态对象,再把动态对象里的详情部分转换为RITMDetails:

dynamic dynamicResponse = JsonConvert.DeserializeObject(jsonResponse);
// 遍历result下的动态属性(这里只有一个)
foreach (var ritmEntry in dynamicResponse.result)
{
    // 把动态值序列化为JSON字符串,再反序列化为RITMDetails
    var ritmDetails = JsonConvert.DeserializeObject<RITMGETRequestResponse.RITMDetails>(
        JsonConvert.SerializeObject(ritmEntry.Value)
    );
    // 访问属性
    string sysId = ritmDetails.Sys_ID;
}

为什么原模型无法生效?

原JSON的result结构是:

"result": {
  "RITM2572913": { /* 详情对象 */ }
}

它是一个包含单个键值对的对象,而你的原模型里result直接是RITMDetails类型,相当于期望result就是详情对象本身,结构不匹配,所以反序列化会失败。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.13 07:53:55