gpt4 book ai didi

python - 未在迭代器中使用时 python yield 的用途

转载 作者:行者123 更新时间:2023-12-04 17:15:44 31 4
gpt4 key购买 nike

我从另一个项目继承了一些相当有问题的代码。其中一个函数是来自库的回调(draw_ui 方法),其中包含 yield 语句。我想知道如果您不在迭代器上下文中使用它来返回值,那么在 python 中使用 yield 的目的是什么。它可能有什么好处?

def draw_ui(self, graphics):
self._reset_components()
imgui.set_next_window_size(200, 200, imgui.ONCE)
if imgui.begin("Entity"):
if not self._selected:
imgui.text("No entity selected")
else:
imgui.text(self._selected.name)
yield
imgui.end() # end entity window

最佳答案

当函数为空时 yield语句,该函数将只返回 None对于第一次迭代,因此您可以说该函数充当生成器,只能迭代一次并产生 None 值:

def foo():
yield
>>> f = foo()
>>> print(next(f))
None
>>> print(next(f))
Traceback (most recent call last):
File "<input>", line 1, in <module>
StopIteration

这就是一个空的 yield做。但是当函数为空时 yield在两个代码块之间,它会执行yield之前的代码对于第一次迭代,以及 yield 之后的代码将在第二次迭代时执行:

def foo():
print('--statement before yield--')
yield
print('--statement after yield--')
>>> f = foo()
>>> next(f)
--statement before yield--
>>> next(f)
--statement after yield--
Traceback (most recent call last):
File "<input>", line 1, in <module>
StopIteration

因此,它以某种方式允许您在中间暂停函数的执行,但是,它会抛出 StopIteration第二次迭代的异常,因为该函数实际上并不 yield第二次迭代的任何内容,为避免这种情况,您可以将默认值传递给 next功能:

看看你的代码,你的函数也在做同样的事情

def draw_ui(self, graphics):
self._reset_components()
imgui.set_next_window_size(200, 200, imgui.ONCE)
if imgui.begin("Entity"):
if not self._selected:
imgui.text("No entity selected")
else:
imgui.text(self._selected.name)
yield #<--------------
imgui.end() #

因此,在调用函数 draw_ui 时, 如果控制转到 else block ,然后在 else block 外划线,即 imgui.end()直到第二次迭代才被调用。

这种类型的实现通常在 ContextManager 中使用,您可以引用以下从 contextlib.contextmanager documentation 复制的代码片段

from contextlib import contextmanager

@contextmanager
def managed_resource(*args, **kwds):
# Code to acquire resource, e.g.:
resource = acquire_resource(*args, **kwds)
try:
yield resource
finally:
# Code to release resource, e.g.:
release_resource(resource)

>>> with managed_resource(timeout=3600) as resource:
... # Resource is released at the end of this block,
... # even if code in the block raises an exception

关于python - 未在迭代器中使用时 python yield 的用途,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/68774978/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com