在导入YAML文件时,为什么在发电机对象迭代后删除内容



我想了解为什么使用pyyAml加载yaml文件后,然后在此生成器对象上执行(获取内容(...变量变为空。

示例

template.yml

doc1:
 atest:                           
   attr: attr0
 btest:                           
   attr: attr1, attr12
 ctest:                           
   attr: attr2, attr22
---
doc2:
 atest:                           
   attr: attr0
 btest:                           
   attr: attr1, attr12
 ctest:                           
   attr: attr2, attr22

python

>>> file = open("template.yml", "r")
>>> content = yaml.safe_load_all(file)
>>> content
>>> <generator object load_all at 0x1079f9518>
>>> for doc in content:
...         print(doc)
... 
{'doc1': {'atest': {'attr': 'attr0'}, 'btest': {'attr': 'attr1, attr12'}, 'ctest': {'attr': 'attr2, attr22'}}}
{'doc2': {'atest': {'attr': 'attr0'}, 'btest': {'attr': 'attr1, attr12'}, 'ctest': {'attr': 'attr2, attr22'}}}
>>> content
<generator object load_all at 0x1079f9518>
>>> for doc in content:
...     print(doc)
... 
>>> 

正如您在上一个呼叫中看到的那样,在第一次没有生成后,再次通过内容变量生成器对象迭代。即使变量仍然作为生成器对象存在,数据也不存在。那为什么要擦干?

另外,我刚刚开始使用yaml,我的第一个想法是:"太好了,这将产生词典的字典",但这是有意义的,这是文档(词典(的列表。对我来说没有意义的是,为什么将YAML文件解析为 Generator对象,而不是列表,因为这就是它的作用。我想我不明白python发电机...他们不只是迭代器吗?

可能有几个原因可以返回生成器对象而不是python中的列表。其中包括效率和数据可用性。

在阅读文档的yaml流中,在内存中加载所有这些文档的记忆效率较小,以防您希望一次对其进行处理,而文档之间很少或没有数据交换。

它也可以随着时间的流逝而更有效,例如对于等待在流中读取第一个文档以显示在屏幕上的人(如果加载第一个文档,显示结果(,然后继续加载第二个文档等的结果。

。 。

,但最重要的原因是数据可用性:如果您要处理流,则该流仍然可以写入并且可能无法完成:其他数据可能会添加到流中的当前YAML文档中,或者其他文档可能会添加被添加到流中。您的文件只是一个流的(无聊的(边缘情况,其中完整的流在前面可用。

如果您具有基于流的API并使用发电机,则可以通过将[]放在生成器周围,可以轻松地将其纳入可重复的列表。但是,进行反向(作为生成器列出列表(并不能使其有效,并且您会等待任何结果列表,直到流关闭为止(即通常,如果上一个文档的最终...,则没有信息在流中不会遵循另一个文档(。

通过Web浏览器和视频显示程序进行类似的处理和介绍,显示程序:

  • 浏览器获取您为URL提供的主页并开始显示它,尽管并非所有图像都加载了。如果您在长页和/或慢速的Internet连接上有很多图像,则可以在完整加载页面之前开始阅读。并且某些图像格式支持在所有数据流入之前显示低分辨率图像的显示。

  • 如果您正在观看视频,则不希望它加载所有视频,然后是所有音频和可能的字幕,然后才开始显示流。如果这是超高清电影流,它可能不适合您的计算机的内存。而且,如果您正在观看现场视频,则所有这些数据甚至都不可用。

这样的基于流的界面以获取数据可能更复杂,但功能更强大。如果您不需要这种功能(因为您有一个完整的流(,那么这种复杂性当然会妨碍您按照您的期望工作。

最新更新