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

C#使用JsonFlatten处理含空格键JSON时Unflatten结构异常如何解决

解决JsonFlatten处理含空格JSON字段时Unflatten拆分错误问题

问题根因

你使用的JsonFlatten包默认的扁平化规则未对包含空格的键做特殊标记,Unflatten操作时会将空格识别为嵌套层级分隔符,因此将原本的单层键First Name错误拆分为两层嵌套结构。

解决方案

方案1:调整JsonFlatten调用参数(改动最小)

调用Flatten方法时传入参数,要求所有含空格的键用方括号包裹,Unflatten会自动识别方括号内的内容为完整键名,不会拆分:

string InputJson = File.ReadAllText(@"C:\Learnings\InputFile.json");
JObject jsonObject = JObject.Parse(InputJson);
// 调整Flatten参数,含空格键用方括号包裹
var flattenedObj = jsonObject.Flatten(
    keySeparator: '.',
    wrapKeyPredicate: key => key.Contains(' '),
    wrapKeyFormat: "[{0}]"
);
var unFlattenObj = flattenedObj.Unflatten(keySeparator: '.', keyWrapper: new SquareBracketKeyWrapper());

var JsonOutput = JsonConvert.SerializeObject(unFlattenObj, Formatting.Indented);
Console.WriteLine(JsonOutput);
File.WriteAllText(@"C:\Learnings\OutputFile.json", JsonOutput);

方案2:自定义实现扁平化/反扁平化逻辑(无需依赖第三方包)

如果第三方包参数不匹配,可以直接基于Newtonsoft.Json实现自定义的扁平化逻辑,完全可控,不会出现特殊字符拆分问题:

// 自定义扁平化方法
public static Dictionary<string, object> FlattenJObject(JObject jObj, string parentPath = "", char separator = '.')
{
    var result = new Dictionary<string, object>();
    foreach (var prop in jObj.Properties())
    {
        var currentPath = string.IsNullOrEmpty(parentPath) ? prop.Name : $"{parentPath}{separator}{prop.Name}";
        if (prop.Value is JObject childObj)
        {
            var childFlatten = FlattenJObject(childObj, currentPath, separator);
            foreach (var kv in childFlatten)
            {
                result.Add(kv.Key, kv.Value);
            }
        }
        else
        {
            result.Add(currentPath, prop.Value.ToObject<object>());
        }
    }
    return result;
}

// 自定义反扁平化方法
public static JObject UnflattenDictionary(Dictionary<string, object> dict, char separator = '.')
{
    var result = new JObject();
    foreach (var kv in dict)
    {
        var parts = kv.Key.Split(separator);
        JToken current = result;
        for (int i = 0; i < parts.Length; i++)
        {
            var part = parts[i];
            if (i == parts.Length - 1)
            {
                if (current is JObject currentObj)
                {
                    currentObj[part] = JToken.FromObject(kv.Value);
                }
            }
            else
            {
                if (current[part] == null)
                {
                    current[part] = new JObject();
                }
                current = current[part];
            }
        }
    }
    return result;
}

调用时直接替换原有逻辑即可,可直接在扁平化后删除指定字段:

string InputJson = File.ReadAllText(@"C:\Learnings\InputFile.json");
JObject jsonObject = JObject.Parse(InputJson);
var flattenedObj = FlattenJObject(jsonObject);
// 此处可执行删除指定字段的逻辑,示例:
// flattenedObj.Remove("Age");
// flattenedObj.Remove("Employement Details.SalaryReceived");
var unFlattenObj = UnflattenDictionary(flattenedObj);

var JsonOutput = JsonConvert.SerializeObject(unFlattenObj, Formatting.Indented);
Console.WriteLine(JsonOutput);
File.WriteAllText(@"C:\Learnings\OutputFile.json", JsonOutput);

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

相关产品推荐
方舟 Agent Plan

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

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