Python 有没有办法强制ruamel在换行符之前在OrderedDict中插入一个新的(键:值)对?
有了下面的代码片段,我将尝试更新“a”下的每个3x ordereddict对象:Python 有没有办法强制ruamel在换行符之前在OrderedDict中插入一个新的(键:值)对?,python,ruamel.yaml,Python,Ruamel.yaml,有了下面的代码片段,我将尝试更新“a”下的每个3x ordereddict对象: import sys from ruamel.yaml import round_trip_load, round_trip_dump s=""" a: - b: c - d: e - f: g """ yaml_obj=round_trip_load(s) yaml_sub_obj = [x for x in yaml_obj['a']] for sub_obj in yaml_sub_obj: su
import sys
from ruamel.yaml import round_trip_load, round_trip_dump
s="""
a:
- b: c
- d: e
- f: g
"""
yaml_obj=round_trip_load(s)
yaml_sub_obj = [x for x in yaml_obj['a']]
for sub_obj in yaml_sub_obj:
sub_obj.insert(1, "new_key", "new_value")
当使用往返转储(yaml\u obj,sys.stdout)
时,我期待下面的输出(空行应该在第一个子元素的最后一个键值对之后):
但是,使用往返转储(yaml\u obj,sys.stdout)
转储初始对象时,将显示:
a:
- b: c
new_key: new_value
- d: e
new_key: new_value
- f: g
new_key: new_value
2) 如果已经存在键,则更新对象的行为是可以的,但我不想强制存在此(键/空_值)对,因为我正在处理的YAML有点复杂,我希望自动填充它们:
s2="""
a:
- b: c
new_key:
- c: d
new_key:
- e: f
new_key:
"""
y = round_trip_load(s2)
for s in y["a"]:
s["new_key"]="new_value"
再次倾倒看起来很好:
a:
- b: c
new_key: new_value
- c: d
new_key: new_value
- e: f
new_key: new_value
我在0.16.5上看到了这种行为,但是我将ruamel.yaml升级到了0.16.10,并且行为是相同的。如果未指定流样式,这是预期行为吗?您的预期不正确。如其他位置所示(例如。 )在ruamel.yaml评论中 与以前的节点关联,这些节点由 映射的键(或序列的索引) 和整行注释,以及空行当前被处理为前一行结束注释的延续,无论 这些EOL注释是否存在 除此之外,您应该考虑使用已经存在很长时间的新API,而不是
往返加载/dump()
函数
import sys
import ruamel.yaml
yaml_str = """\
a:
- b: c
- d: e
- f: g
"""
yaml = ruamel.yaml.YAML()
data = yaml.load(yaml_str)
for sub_obj in data['a']:
index = 1
new_key = "new_key"
prev_key = list(sub_obj.keys())[index-1]
sub_obj.insert(index, new_key, "new_value")
try:
sub_obj.ca.items[new_key] = sub_obj.ca.items.pop(prev_key)
except KeyError:
pass
yaml.dump(data, sys.stdout)
其中:
a:
- b: c
new_key: new_value
- d: e
new_key: new_value
- f: g
new_key: new_value
a:
- b: c # some comment
new_key: new_value
# this is to make an emtpy line more clearly visible
- d: e
new_key: new_value
- f: g
new_key: new_value
如果您有具体的行末注释,那么
您不应该弹出prev_键
,而是复制它并拆分它的第三个元素
import sys
from copy import deepcopy
import ruamel.yaml
yaml_str = """\
a:
- b: c # some comment
# this is to make an emtpy line more clearly visible
- d: e
- f: g
"""
yaml = ruamel.yaml.YAML()
data = yaml.load(yaml_str)
for sub_obj in data['a']:
index = 1
new_key = "new_key"
prev_key = list(sub_obj.keys())[index-1]
sub_obj.insert(index, new_key, "new_value")
try:
comment = sub_obj.ca.items[prev_key]
new_comment = deepcopy(comment)
comment[2].value, rest = comment[2].value.split('\n', 1)
new_comment[2].value = '\n' + rest
sub_obj.ca.items[new_key] = new_comment
except KeyError:
pass
yaml.dump(data, sys.stdout)
其中:
a:
- b: c
new_key: new_value
- d: e
new_key: new_value
- f: g
new_key: new_value
a:
- b: c # some comment
new_key: new_value
# this is to make an emtpy line more clearly visible
- d: e
new_key: new_value
- f: g
new_key: new_value
请注意,这不是一个用于处理评论的已发布API,可以/将
更改,因此请锁定适合您的应用程序的ruamel.yaml版本
项目。您的期望不正确。如其他位置所示(例如。
)在ruamel.yaml评论中
与以前的节点关联,这些节点由
映射的键(或序列的索引)
和整行注释,以及空行当前被处理为前一行结束注释的延续,无论
这些EOL注释是否存在
除此之外,您应该考虑使用已经存在很长时间的新API,而不是往返加载/dump()
函数
import sys
import ruamel.yaml
yaml_str = """\
a:
- b: c
- d: e
- f: g
"""
yaml = ruamel.yaml.YAML()
data = yaml.load(yaml_str)
for sub_obj in data['a']:
index = 1
new_key = "new_key"
prev_key = list(sub_obj.keys())[index-1]
sub_obj.insert(index, new_key, "new_value")
try:
sub_obj.ca.items[new_key] = sub_obj.ca.items.pop(prev_key)
except KeyError:
pass
yaml.dump(data, sys.stdout)
其中:
a:
- b: c
new_key: new_value
- d: e
new_key: new_value
- f: g
new_key: new_value
a:
- b: c # some comment
new_key: new_value
# this is to make an emtpy line more clearly visible
- d: e
new_key: new_value
- f: g
new_key: new_value
如果您有具体的行末注释,那么
您不应该弹出prev_键
,而是复制它并拆分它的第三个元素
import sys
from copy import deepcopy
import ruamel.yaml
yaml_str = """\
a:
- b: c # some comment
# this is to make an emtpy line more clearly visible
- d: e
- f: g
"""
yaml = ruamel.yaml.YAML()
data = yaml.load(yaml_str)
for sub_obj in data['a']:
index = 1
new_key = "new_key"
prev_key = list(sub_obj.keys())[index-1]
sub_obj.insert(index, new_key, "new_value")
try:
comment = sub_obj.ca.items[prev_key]
new_comment = deepcopy(comment)
comment[2].value, rest = comment[2].value.split('\n', 1)
new_comment[2].value = '\n' + rest
sub_obj.ca.items[new_key] = new_comment
except KeyError:
pass
yaml.dump(data, sys.stdout)
其中:
a:
- b: c
new_key: new_value
- d: e
new_key: new_value
- f: g
new_key: new_value
a:
- b: c # some comment
new_key: new_value
# this is to make an emtpy line more clearly visible
- d: e
new_key: new_value
- f: g
new_key: new_value
请注意,这不是一个用于处理评论的已发布API,可以/将
更改,因此请锁定适合您的应用程序的ruamel.yaml版本
项目。AFAICTflow\u style
即使使用旧式例程,也不会影响此行为。AFAICTflow\u style
即使使用旧式例程,也不会影响此行为。谢谢你,Anthon!我对你的回答投了赞成票。它解决了那个特殊的问题,我试着从我的“现实生活”问题开始尽可能地简化这个问题。我的yaml更复杂,没有“new_value”,而是嵌套字典(例如:“new_key”:{“new_dict_key”:“new_dict_value”})。因此,空行将显示在“new_key”之后,但在“new_dict_key”之前,这显然是意料之中的:a:-b:c#一些注释new_key:#这是为了使空行更清晰可见new_dict_key:new_dict_value我将尝试使用新API挖掘更多内容。谢谢!谢谢你,安顿!我对你的回答投了赞成票。它解决了那个特殊的问题,我试着从我的“现实生活”问题开始尽可能地简化这个问题。我的yaml更复杂,没有“new_value”,而是嵌套字典(例如:“new_key”:{“new_dict_key”:“new_dict_value”})。因此,空行将显示在“new_key”之后,但在“new_dict_key”之前,这显然是意料之中的:a:-b:c#一些注释new_key:#这是为了使空行更清晰可见new_dict_key:new_dict_value我将尝试使用新API挖掘更多内容。谢谢!