Python使用ruamel.yaml序列化按层级控制键引号及流格式方案求教
解决方案
实现思路
- 自定义ruamel.yaml的序列化Representer,新增字典嵌套深度计数属性,处理映射时自动更新深度,完全按照数据结构层级控制键的引号规则,无需硬编码任何键名,适配键名频繁变更的业务场景
- 调整ruamel.yaml的flow格式相关配置,实现序列显示
[]、映射显示{}的多行缩进输出效果
完整实现代码
import ruamel.yaml import sys # 自定义支持分层控制引号的Representer class LayeredQuoteRepresenter(ruamel.yaml.RoundTripRepresenter): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) # 字典嵌套深度计数,列表作为容器不参与深度计算 self.dict_depth = 0 def represent_mapping(self, tag, mapping, flow_style=None): # 进入映射层级前深度+1,处理完成后回溯深度 self.dict_depth += 1 node = super().represent_mapping(tag, mapping, flow_style=flow_style) self.dict_depth -= 1 return node def represent_key(self, key_data): # 引号规则:仅根下第一层字典(深度为2)的键加双引号,其余层级键无引号 if self.dict_depth != 2: key_data = ruamel.yaml.scalarstring.PlainScalarString(key_data) return self.represent_data(key_data) # 初始化YAML实例 yaml = ruamel.yaml.YAML() yaml.Representer = LayeredQuoteRepresenter yaml.default_flow_style = True # 启用flow格式,显示{}、[]符号 yaml.default_style = '"' # 字符串值默认加双引号 yaml.indent(mapping=4, sequence=4, offset=2) # 缩进配置,可调整offset匹配你需要的缩进效果 yaml.explicit_start = True # 开头显示--- yaml.compact = False # flow格式不压缩,每个元素单独换行 yaml.trailing_comma = True # 集合最后一个元素后保留逗号 yaml.split_lines = True # 测试数据 data2 = {'bar': 'var', 'lar': 'nar'} data = {'foo': [{ 'zar': 'mar', 'car': [data2] }]} # 输出结果 yaml.dump(data, sys.stdout)
输出效果
--- foo: [ { "car": [ { bar: "var", lar: "nar", }, ], "zar": "mar", }, ]
内容的提问来源于stack exchange,提问作者NelBassist
相关产品推荐
相关产品推荐

