Python 中的产量中断

发布于 2024-11-16 01:45:35 字数 548 浏览 3 评论 0原文

根据这个问题的答案,C#中的yieldbreak相当于Python中的return。在正常情况下,return 确实会停止生成器。但是如果你的函数除了 return 之外什么都不做,你会得到一个 None,而不是一个空迭代器,它是由 C# 中的yield break 返回的

def generate_nothing():
    return

for i in generate_nothing():
    print i

。得到一个 TypeError: 'NoneType' object is not iterable, 但如果我添加并且在 return 之前从未运行 yield,则此函数将返回我所期望的结果。

def generate_nothing():
    if False: yield None
    return

它有效,但看起来很奇怪。你有更好的主意吗?

According to answer to this question, yield break in C# is equivalent to return in Python. In the normal case, return indeed stops a generator. But if your function does nothing but return, you will get a None not an empty iterator, which is returned by yield break in C#

def generate_nothing():
    return

for i in generate_nothing():
    print i

You will get a TypeError: 'NoneType' object is not iterable,
but if I add and never run yield before return, this function returns what I expect.

def generate_nothing():
    if False: yield None
    return

It works, but seems weird. Do you have a better idea?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

墨落成白 2024-11-23 01:45:36

有趣的是,这两个函数具有相同的字节码。当字节码编译器找到 yield 关键字时,可能有一个标志设置为 generator

>>> def f():
...   return

>>> def g():
...   if False: yield 
#in Python2 you can use 0 instead of False to achieve the same result


>>> from dis import dis
>>> dis(f)
2           0 LOAD_CONST               0 (None) 
            3 RETURN_VALUE
>>> dis(g)
2           0 LOAD_CONST               0 (None) 
            3 RETURN_VALUE

The funny part is that both functions have the same bytecode. Probably there's a flag that sets to generator when bytecode compiler finds the yield keyword.

>>> def f():
...   return

>>> def g():
...   if False: yield 
#in Python2 you can use 0 instead of False to achieve the same result


>>> from dis import dis
>>> dis(f)
2           0 LOAD_CONST               0 (None) 
            3 RETURN_VALUE
>>> dis(g)
2           0 LOAD_CONST               0 (None) 
            3 RETURN_VALUE
简单气质女生网名 2024-11-23 01:45:35
def generate_nothing():
    return
    yield
def generate_nothing():
    return
    yield
脱离于你 2024-11-23 01:45:35

处理这个问题的一个好方法是引发 StopIteration ,这是当你的迭代器有没有任何东西可以让出并且调用 next() 。这也将优雅地跳出 for 循环,循环内不执行任何内容。

例如,给定一个元组 (0, 1, 2, 3) 我想获得重叠的对 ((0, 1), (1, 2), (2, 3))。我可以这样做:

def pairs(numbers):
    if len(numbers) < 2:
        raise StopIteration

    for i, number in enumerate(numbers[1:]):
        yield numbers[i], number

现在 pairs 可以安全地处理包含 1 个或更少数字的列表。

A good way to handle this is raising StopIteration which is what is raised when your iterator has nothing left to yield and next() is called. This will also gracefully break out of a for loop with nothing inside the loop executed.

For example, given a tuple (0, 1, 2, 3) I want to get overlapping pairs ((0, 1), (1, 2), (2, 3)). I could do it like so:

def pairs(numbers):
    if len(numbers) < 2:
        raise StopIteration

    for i, number in enumerate(numbers[1:]):
        yield numbers[i], number

Now pairs safely handles lists with 1 number or less.

平定天下 2024-11-23 01:45:35
def generate_nothing():
    return iter([])
def generate_nothing():
    return iter([])
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文