diff --git a/Lib/test/test_dis.py b/Lib/test/test_dis.py index 58ba86fb43092a..b53a3656429300 100644 --- a/Lib/test/test_dis.py +++ b/Lib/test/test_dis.py @@ -204,7 +204,6 @@ def bug1333982(x=[]): LOAD_CONST 1 ( at 0x..., file "%s", line %d>) MAKE_FUNCTION LOAD_FAST_BORROW 0 (x) - GET_ITER CALL 0 %3d LOAD_SMALL_INT 1 @@ -821,7 +820,6 @@ def foo(x): MAKE_FUNCTION SET_FUNCTION_ATTRIBUTE 8 (closure) LOAD_DEREF 1 (y) - GET_ITER CALL 0 CALL 1 RETURN_VALUE diff --git a/Lib/test/test_generators.py b/Lib/test/test_generators.py index 8bce42f037478c..3e41c7b9663491 100644 --- a/Lib/test/test_generators.py +++ b/Lib/test/test_generators.py @@ -268,6 +268,28 @@ def loop(): #This should not raise loop() + def test_genexpr_only_calls_dunder_iter_once(self): + + class Iterator: + + def __init__(self): + self.val = 0 + + def __next__(self): + if self.val == 2: + raise StopIteration + self.val += 1 + return self.val + + # No __iter__ method + + class C: + + def __iter__(self): + return Iterator() + + self.assertEqual([1,2], list(i for i in C())) + class ModifyUnderlyingIterableTest(unittest.TestCase): iterables = [ diff --git a/Lib/test/test_genexps.py b/Lib/test/test_genexps.py index 7fb58a67368576..fe5f18fa3f88a0 100644 --- a/Lib/test/test_genexps.py +++ b/Lib/test/test_genexps.py @@ -123,15 +123,6 @@ >>> list(g) [0, 1, 4, 9, 16, 25, 36, 49, 64, 81] -Verify that the outermost for-expression makes an immediate check -for iterability - - >>> (i for i in 6) - Traceback (most recent call last): - File "", line 1, in -toplevel- - (i for i in 6) - TypeError: 'int' object is not iterable - Verify late binding for the outermost if-expression >>> include = (2,4,6,8) diff --git a/Misc/NEWS.d/next/Core_and_Builtins/2025-04-10-10-29-45.gh-issue-127682.X0HoGz.rst b/Misc/NEWS.d/next/Core_and_Builtins/2025-04-10-10-29-45.gh-issue-127682.X0HoGz.rst new file mode 100644 index 00000000000000..b87750eb516e7a --- /dev/null +++ b/Misc/NEWS.d/next/Core_and_Builtins/2025-04-10-10-29-45.gh-issue-127682.X0HoGz.rst @@ -0,0 +1,4 @@ +No longer call ``__iter__`` twice when creating and executing a generator expression. +Creating a generator expression from a non-interable will raise only when the +generator expression is executed. +This brings the behavior of generator expressions in line with other generators. diff --git a/Python/codegen.c b/Python/codegen.c index 379d37c65ca8e6..35b46dcdc40950 100644 --- a/Python/codegen.c +++ b/Python/codegen.c @@ -4775,10 +4775,7 @@ codegen_comprehension(compiler *c, expr_ty e, int type, } Py_CLEAR(co); - if (codegen_comprehension_iter(c, outermost)) { - goto error; - } - + VISIT(c, expr, outermost->iter); ADDOP_I(c, loc, CALL, 0); if (is_async_comprehension && type != COMP_GENEXP) { pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy