python yaml.dump()中的强制缩进

2024-03-29 07:48:59 发布

您现在位置:Python中文网/ 问答频道 /正文

编写了一些python(3.7)代码将json转储到yaml,并将结果插入另一个yaml代码,如:

sample_code = '''
A :
  - DATA_A

B :
  C :
    {}
'''

import yaml

json_code = { 'json' : { D: VALUE_D, E: VALUE_E } }
sample_code.format( yaml.dump(json_code) )

将格式化代码写入文件后,我得到:

A :
  - DATA_A
B :
  C :
    json :
  D : VALUE_D
  E : VALUE_E

我希望得到如下结果:

A :
  - DATA_A
B :
  C :
    json :
      D : VALUE_D
      E : VALUE_E

我只是用了一种不成形的方法:

json_code_dumped = yaml.dump(json_code).replace("  ", "          ")
samplecode.format( json_code_dumped )

现在不管怎样,这都是可行的。 有没有更聪明的办法

多谢各位


Tags: 文件sample方法代码importjsonformatyaml
1条回答
网友
1楼 · 发布于 2024-03-29 07:48:59

正确的方法是将整个YAML数据作为内存数据加载,并在其中插入JSON数据。这保证了倾倒将产生有效的YAML

现在有不同的方法来解决这个问题。这是最简单的一个:

import yaml

sample_code = '''
A :
  - DATA_A

B :
  C : {}
'''

data = yaml.safe_load(sample_code)
data["B"]["C"]["json"] = { "D": "VALUE_D", "E": "VALUE_E" }
print(yaml.dump(data))

{}现在被解释为空映射,因为它是用YAML加载的。这就是为什么可以在其中放入"json"键。输出如下所示:

A:
- DATA_A
B:
  C:
    json:
      D: VALUE_D
      E: VALUE_E

格式更改是因为YAML不保留格式(有关详细信息,请参阅this question


一种更复杂的方法是this question的答案,它使用低级事件API,因此允许您指定要在字符串列表中插入的位置,并允许您更详细地指定所需的标量格式。但是,它要复杂得多,需要您将附加数据作为YAML事件提供。但是,如果您有实际的JSON输入,则可以将其加载到YAML事件中,因为YAML是JSON的超集


下面是第三种方法,可以像当前一样在YAML文件中指定占位符:

from yaml.loader import SafeLoader
import yaml

class MyLoader(SafeLoader):
  def __init__(self, stream):
    SafeLoader.__init__(self, stream)
    self.replacements = []

def replace_placeholder(loader, node):
  index = int(loader.construct_scalar(node))
  return loader.replacements[index]

MyLoader.add_constructor('!placeholder', replace_placeholder)


sample_code = '''
A :
  - DATA_A

B :
  C : !placeholder 0
'''

loader = MyLoader(sample_code)
loader.replacements.append(
  { 'json' : { 'D': 'VALUE_D', 'E': 'VALUE_E' }})
print(yaml.dump(loader.get_single_data()))

format非常相似,YAML文件中有一个占位符,由本地标记!placeholder标识。我给它一个数字,表明你可以有多个占位符。您将要替换占位符的数据放入加载器的replacements中,然后在加载过程中,我们的自定义构造函数将用实际数据替换占位符。结果与第一种方法相同

相关问题 更多 >