[Python-Dev] Iteration variables and list comprehensions (original) (raw)

David Beazley beazley@cs.uchicago.edu
Tue, 29 May 2001 11:56:09 -0500 (CDT)


I'm not sure if this has ever been brought up before (I don't recall seeing it), but I would like to throw out something that has been bugging me about list comprehensions for quite some time...

First of all, I have to say that I've really grown to like list comprehensions a lot. In fact, I find myself using them in just about every Python program I've been writing since switching to Python 2.0. However, I've also been shooting myself in the foot a little more than usual due to the following issue:

When I write a list comprehension like this:

s = [ expr(x) for x in t ]

it is VERY easy to overlook the fact that the iteration variable "x" is evaluated in the local scope (and replaces any previous binding to "x" that might have existed outside the context of the list comprehension). Because of this, I have frequently found myself debugging the following programming error:

Some loop

for x in r: ... # bunch of statements ... s = [expr(x) for x in t] ... # Try to do something with x. # ???? What in the hell is wrong with my program ???? ...

The main problem is that I conceptually tend to think of the list comprehension as being some kind of list operator where the index name is really one of the operands in some sense. Because of this, it is VERY easy to get in the habit of throwing list comprehensions all over the place, each of which uses a common index name like x,i,j, etc. Of course, this works just fine until you forget that you're also using x,i,j for some kind of loop variable someplace else :-).

Therefore, I'm wondering if it would make any sense to make the iterator variables used inside of a list comprehension private in some manner--either through name mangling or some other technique? For example:

s = [expr(x) for x in t]

would get expanded into something roughly like this:

s = [ ] for _mangled_x in t: s.append(expr(_mangled_x)) del _mangled_x

Just as an aside, I have never intentionally used the iterator variable of a list comprehension after the operation has completed. I was actually quite surprised with this behavior the first time I saw it. I suspect most other programmers would not anticipate this side effect either.

Comments?

Cheers,

Dave