ruamel-yaml 0.18.10版本中如何保留多行字符串的反斜杠
我完全理解你的困扰——你希望用ruamel-yaml读取并重新写入YAML文件时,能保留原文件里多行字符串末尾的反斜杠(也就是YAML的行续接符)。从你给出的前后代码对比来看,原YAML里的[Assignment:\在dump后变成了[Assignment:,那个关键的反斜杠不见了。
先给你理清背后的原因:原YAML中的反斜杠是YAML语法层面的行续接符,并不是字符串内容的一部分。ruamel-yaml在默认的round-trip加载过程中,会自动解析这个行续接符,把拆分的两行合并成一个完整的字符串,所以dump时自然不会再生成这个反斜杠,只会输出合并后的内容。
针对这个需求,我给你两种可行的解决方案:
方法一:调整输出宽度,让ruamel-yaml自动生成行续接符
ruamel-yaml有个width参数,当字符串长度超过设定的阈值时,会自动拆分字符串并添加行续接符。你可以根据原文件的换行位置,设置一个合适的宽度值:
import pathlib from ruamel.yaml import YAML control_file = 'xx/nist_ocp4.yml' yaml = YAML() yaml.preserve_quotes = True yaml.width = 60 # 可以根据原文件的换行位置微调这个数值 d = yaml.load(pathlib.Path(control_file)) yaml.dump(d, pathlib.Path(control_file))
这种方法不需要手动修改字符串内容,让ruamel-yaml自动匹配原有的换行风格,生成带行续接符的输出。
方法二:手动标记字符串为保留原始格式
如果需要完全精确地还原原文件的换行和反斜杠结构,可以用PreservedScalarString包裹目标字符串,强制ruamel-yaml按照你指定的格式输出:
import pathlib from ruamel.yaml import YAML from ruamel.yaml.scalarstring import PreservedScalarString control_file = 'xx/nist_ocp4.yml' yaml = YAML() yaml.preserve_quotes = True d = yaml.load(pathlib.Path(control_file)) # 注意:因为原解析后的字符串已经丢失了行续接符,需要手动还原原始格式 original_description = "The organization:\n a. Develops, documents, and disseminates to [Assignment:\ or whenever a significant change occurs]" d['controls'][0]['description'] = PreservedScalarString(original_description) yaml.dump(d, pathlib.Path(control_file))
这种方法适合需要严格控制输出格式的场景,但需要你手动还原带行续接符的原始字符串。
另外补充个小知识点:如果你的需求是让字符串内容本身包含反斜杠(而不是YAML的行续接符),那原YAML里需要用双反斜杠\\来表示单个反斜杠,这样ruamel-yaml解析后会保留这个反斜杠,dump时也能正确输出。
备注:内容来源于stack exchange,提问作者Alex Xuan

