如何使用C#拆分无分隔符的拼接JSON文件?
这个问题我之前处理过好几次——大体积的无分隔符JSON拼接文件确实头疼,既要高效不爆内存,又得精准避开字符串里的假分界符。下面给你两个实用方案,都是流式处理,速度拉满还不会拆错:
核心思路:别粗暴匹配,要跟踪JSON状态
直接按{或}拆分肯定会翻车,比如字符串里的"content": "This is a {test}"会被误判。正确的做法是逐字符/逐块扫描时,同步跟踪三个关键状态:
- 是否处于双引号包裹的字符串内
- 前一个字符是否是转义符
\(避免把\"当成字符串结束) - 大括号的嵌套层级(只有当层级回到0且不在字符串内时,才是一个完整的JSON对象)
方案一:Python流式处理脚本(灵活易扩展)
这个脚本用生成器流式读取文件,全程只保留当前正在处理的对象缓冲区,内存占用极低,GB级文件也能轻松应对:
def split_concat_json(file_path): buffer = [] in_string = False escaped = False brace_depth = 0 # 按块读取(4096字节是平衡速度和内存的常用值) with open(file_path, 'r', encoding='utf-8') as f: while chunk := f.read(4096): for char in chunk: if escaped: escaped = False buffer.append(char) continue if char == '\\': escaped = True buffer.append(char) continue if char == '"': in_string = not in_string buffer.append(char) continue # 只在非字符串状态下跟踪大括号层级 if not in_string: if char == '{': brace_depth += 1 elif char == '}': brace_depth -= 1 # 层级回到0,说明当前对象完整 if brace_depth == 0: buffer.append(char) yield ''.join(buffer) buffer = [] continue buffer.append(char) # 处理文件末尾剩余的完整对象 if buffer and brace_depth == 0 and not in_string: yield ''.join(buffer) # 使用示例:拆分后保存为单独文件 for idx, json_obj in enumerate(split_concat_json('your_large_file.json'), 1): with open(f'output_{idx}.json', 'w', encoding='utf-8') as out_f: out_f.write(json_obj)
方案二:Awk命令行脚本(适合Linux/macOS快速处理)
如果不想写Python,用Awk写个单行脚本也能搞定,适合终端环境下的批量处理:
BEGIN { in_string = 0 escaped = 0 brace_depth = 0 buffer = "" } { for (i = 1; i <= length($0); i++) { char = substr($0, i, 1) if (escaped) { buffer = buffer char escaped = 0 continue } if (char == "\\") { buffer = buffer char escaped = 1 continue } if (char == "\"") { in_string = 1 - in_string buffer = buffer char continue } if (!in_string) { if (char == "{") { brace_depth++ } else if (char == "}") { brace_depth-- if (brace_depth == 0) { buffer = buffer char print buffer buffer = "" continue } } } buffer = buffer char } } END { if (buffer != "" && brace_depth == 0 && !in_string) { print buffer } }
使用方法:把脚本存为split_json.awk,然后执行:
awk -f split_json.awk your_large_file.json > combined_output.json # 如果要拆分到单独文件,可以结合xargs: awk -f split_json.awk your_large_file.json | xargs -I {} sh -c 'echo "{}" > output_$((++n)).json'
关键注意事项
- 确保文件编码是UTF-8,如果是其他编码(比如GBK),需要调整脚本里的编码参数
- 先拿小测试文件验证,比如包含转义字符串的
{"msg":"He said \"Hi!\""},确保不会误拆分 - 如果文件里混有JSON数组而非纯对象,需要微调层级判断逻辑(比如跟踪
[]的层级)
内容的提问来源于stack exchange,提问作者Martin Brown
相关产品推荐
相关产品推荐

