写入JSON时如何压缩全相同值长列表且不修改原始字典
解决方案
实现思路
- 首先明确:你需要的简写语法属于Python语法规范,不属于标准JSON语法,因此无法直接通过
json.dump实现,我们可以自定义序列化函数输出Python格式的配置文件,使用时直接导入即可,比JSON解析更便捷。 - 核心判断逻辑:遍历配置结构中的所有列表,判定是否所有元素完全相同,满足条件则输出简写格式,否则按常规方式展开,你可以自行调整触发简写的列表长度阈值。
代码实现
def serialize_config(obj, indent=0): indent_str = " " * 4 * indent if isinstance(obj, dict): items = [] for k, v in obj.items(): serialized_v = serialize_config(v, indent+1) items.append(f"{indent_str} {repr(k)}: {serialized_v},") return "{\n" + "\n".join(items) + f"\n{indent_str}}}" elif isinstance(obj, list): # 长度小于10的短列表正常输出,可按需调整阈值 if len(obj) < 10: return repr(obj) # 判断是否所有元素相同 first_val = obj[0] if all(x == first_val for x in obj): return f"[{repr(first_val)}] * {len(obj)}" else: return repr(obj) else: return repr(obj) # 使用示例 if __name__ == "__main__": # 你的原始config字典,无需修改 config = { "key1": [0.2] * 10000, "key2": 0.3, "key3": { "subkey1": [0.0] * 100, "subkey2": "ya ba da bi do", }, "key4": "Wubba Lubba Dub Dub" } # 写入配置文件 with open("config.py", "w", encoding="utf-8") as f: f.write(f"config = {serialize_config(config)}\n") # 后续加载配置时直接导入即可 # from config import config
兼容JSON的备选方案
如果需要输出标准JSON格式,可以把同值长列表转换为特殊标记结构存储,加载时自动还原:
- 序列化时把符合条件的列表转为
{"__repeat__": true, "val": 0.2, "cnt": 100000} - 反序列化时遍历JSON结构,识别到
__repeat__标记就自动还原为[val]*cnt
这种方式也能大幅降低文件体积,同时兼容JSON生态。
内容的提问来源于stack exchange,提问作者Yomach
相关产品推荐
相关产品推荐

