[Python-3000] Is this a bug with list comprehensions or not?

Antoine Pitrou solipsis at pitrou.net
Thu Jul 10 15:28:01 CEST 2008


Carl Johnson <carl <at> carlsensei.com> writes:
> 
> However, it can be argued that in Python 3 list comprehensions should be
> thought of as "syntatic sugar" for ``list(generator expression)`` not a
> for-loop with an accumulator. (This seems to be the motivation for no
> longer "leaking" variables from list comprehensions into their enclosing
> namespace.)

I don't know the exact history but I think leaking the iteration variable
didn't have any practical use and could be the possible cause of subtle bugs,
which is a sufficient reason for changing that behaviour. Consistency is an
added bonus :-)

> This raises the question, do we need both a ``break`` statement and
> ``raise StopIteration``? Can the former just be made into syntatic sugar
> for the later? Or is this the hobgoblin of a little mind?

I'd say the latter :-)

Also, I don't see where consistency is improved. IMO, StopIteration is meant to
be raised by the code which produces the iterator, not by the code consuming it
- and even less by third-party, non-iterator related code. Otherwise it's an
application bug.

That is, in your example:

 >>> def f(x):
...  if x > 5: raise StopIteration
...
 >>> list(x for x in range(100) if not f(x))
[0, 1, 2, 3, 4, 5]

f() certainly shouldn't raise a StopIteration. There's no reason for doing
that, other than taking dirty implementation shortcuts and ending up with
difficult to maintain code.

(if you want to stop an iterator based on some predicate you can use
itertools.takewhile())

Regards

Antoine.




More information about the Python-3000 mailing list