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

如何用System.Text.Json反序列化含额外属性的字典式JSON?

解决方案

针对这种混合固定属性(traceId)和动态日期键的JSON结构,以下是两种基于System.Text.Json的可行处理方案:

方案一:用JsonExtensionData定义根类(推荐)

创建包含固定属性和动态数据的根类,通过JsonExtensionData自动收集未显式定义的日期键,再转换为FreeSlots对象:

public class FreeSlotsResponse
{
    [JsonPropertyName("traceId")]
    public string? TraceId { get; set; }

    [JsonExtensionData]
    private Dictionary<string, JsonElement> _dynamicDateData { get; set; } = new();

    // 转换并返回日期与FreeSlots的映射
    public Dictionary<string, FreeSlots> DateToFreeSlots
    {
        get
        {
            var result = new Dictionary<string, FreeSlots>();
            foreach (var kvp in _dynamicDateData)
            {
                var freeSlots = JsonSerializer.Deserialize<FreeSlots>(kvp.Value);
                result.Add(kvp.Key, freeSlots!);
            }
            return result;
        }
    }
}

// 原FreeSlots类保持不变
public class FreeSlots
{
    [JsonConstructor]
    public FreeSlots(){}

    [JsonPropertyName("slots")]       
    public List<string>? slots;
}

使用方式

直接反序列化为根类,即可同时获取traceId和日期对应的FreeSlots:

string jsonResponse = "你的API响应JSON字符串";
var response = JsonSerializer.Deserialize<FreeSlotsResponse>(jsonResponse);

// 访问traceId
string? traceId = response?.TraceId;

// 访问日期对应的FreeSlots集合
var dateSlots = response?.DateToFreeSlots;

方案二:直接解析JsonDocument(灵活处理)

若不想额外定义根类,可直接解析JsonDocument,手动提取traceId并转换日期键:

string jsonResponse = "你的API响应JSON字符串";
using var doc = JsonDocument.Parse(jsonResponse);
var rootElement = doc.RootElement;

// 提取traceId
string? traceId = rootElement.TryGetProperty("traceId", out var traceIdElement) 
    ? traceIdElement.GetString() 
    : null;

// 转换日期键到FreeSlots字典
var dateSlots = new Dictionary<string, FreeSlots>();
foreach (var property in rootElement.EnumerateObject())
{
    if (property.Name != "traceId")
    {
        var freeSlots = property.Value.Deserialize<FreeSlots>();
        dateSlots.Add(property.Name, freeSlots!);
    }
}

问题原因说明

你之前直接反序列化为Dictionary<string, JsonElement>时,traceId会被当作字典的一个键而非独立属性,若后续反序列化FreeSlots时未正确匹配JSON结构,就可能导致slots为空。上述两种方案均规避了该问题,同时保留了traceId的提取逻辑。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.11 02:15:24