Author: Carl Friedrich Bolz-Tereick <[email protected]>
Branch: py3.7
Changeset: r98622:7a0cdcf24b94
Date: 2020-01-31 23:01 +0100
http://bitbucket.org/pypy/pypy/changeset/7a0cdcf24b94/
Log: gah! turning StopIteration to RuntimeError in generators broke the
applevel implementation of iter with sentinel!
diff --git a/pypy/interpreter/generator.py b/pypy/interpreter/generator.py
--- a/pypy/interpreter/generator.py
+++ b/pypy/interpreter/generator.py
@@ -163,6 +163,7 @@
self.frame.w_yielding_from = w_delegate
def _leak_stopiteration(self, e):
+ import pdb; pdb.set_trace()
# turn a leaking StopIteration into RuntimeError (with its cause set
# appropriately).
space = self.space
diff --git a/pypy/interpreter/test/apptest_generator.py
b/pypy/interpreter/test/apptest_generator.py
--- a/pypy/interpreter/test/apptest_generator.py
+++ b/pypy/interpreter/test/apptest_generator.py
@@ -803,6 +803,21 @@
with raises(RuntimeError):
next(badgenerator(5))
+def test_stopiteration_can_be_caught():
+ def g():
+ raise StopIteration
+ def finegenerator(x):
+ yield x
+ if x == 5:
+ try:
+ g()
+ except StopIteration:
+ pass
+ yield x
+ gen = finegenerator(5)
+ next(gen) # fine
+ next(gen) # fine
+
def test_generator_stop_cause():
def gen1():
yield 42
diff --git a/pypy/module/__builtin__/operation.py
b/pypy/module/__builtin__/operation.py
--- a/pypy/module/__builtin__/operation.py
+++ b/pypy/module/__builtin__/operation.py
@@ -126,7 +126,10 @@
def iter_generator(callable_, sentinel):
while 1:
- result = callable_()
+ try:
+ result = callable_()
+ except StopIteration:
+ return
if result == sentinel:
return
yield result
diff --git a/pypy/module/__builtin__/test/test_builtin.py
b/pypy/module/__builtin__/test/test_builtin.py
--- a/pypy/module/__builtin__/test/test_builtin.py
+++ b/pypy/module/__builtin__/test/test_builtin.py
@@ -286,17 +286,20 @@
self.value = 0
def __call__(self):
self.value += 1
+ if self.value > 10:
+ raise StopIteration
return self.value
- # XXX Raising errors is quite slow --
- # uncomment these lines when fixed
- #self.assertRaises(TypeError,iter,3,5)
- #self.assertRaises(TypeError,iter,[],5)
- #self.assertRaises(TypeError,iter,{},5)
+ with raises(TypeError):
+ iter(3, 5)
+
x = iter(count(),3)
assert next(x) ==1
assert next(x) ==2
raises(StopIteration, next, x)
+ # a case that runs till the end
+ assert list(iter(count(), 100)) == [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
+
def test_enumerate(self):
import sys
seq = range(2,4)
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit