Could someone help me understand what PEP479 is about? I was reading the doc and couldn't get my head around it.
The abstract says:
This PEP proposes a change to generators: when StopIteration is raised inside a generator, it is replaced it with RuntimeError. (More precisely, this happens when the exception is about to bubble out of the generator's stack frame.)
So for example, does a loop like so still work?
it = iter([1,2,3])
try:
i = next(it)
while True:
i = next(it)
except StopIteration:
pass
Or does it mean that if I have a generator definition like so:
def gen():
yield from range(5)
raise StopIteration
the StopIteration
is going to be replaced with RuntimeError
?
I would really appreciate if someone could shed some light on this.
Your first loop should still work -- StopIteration
will still be raised when a generator is exhausted.
The difference is that there was ambiguity when a StopIteration
was raised in a generator. Did it get raised (implicitly) because the generator ran out of things to yield -- Or did it get raised because a delegate generator ran out of things to yield (maybe due to a next
call) and the exception wasn't handled properly? PEP-0479 tries to address that ambiguity. Now if you get a StopIteration
, it means that the generator you are working with ran out items to yield. Said another way, it means that a delegate generator didn't get mis-handled when running out of items.
To support this change, your generator should return
instead of raising StopIteration
explicitly.
def gen():
yield from range(5)
return
Here's what happens if you try it with the StopIteration
and generator_stop
enabled (which will become the default when python3.7 comes around):
>>> from __future__ import generator_stop
>>> def gen():
... yield from range(5)
... raise StopIteration
...
>>> list(gen())
Traceback (most recent call last):
File "<stdin>", line 3, in gen
StopIteration
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
RuntimeError: generator raised StopIteration