list comprehensions whats happening here

Carlos Ribeiro cribeiro at mail.inet.com.br
Fri Apr 13 09:03:17 EDT 2001


I also lost. I did a small change on your example to better illuminate what 
is happening:

 >>> [[i,j] for i in range(3), for j in 'abc']
[[[0, 1, 2], 'a'], [[0, 1, 2], 'b'], [[0, 1, 2], 'c']]
 >>> [[i,j] for i in range(3), for j in 'abc',]
[[[0, 1, 2], 'abc']]
 >>> [[i,j] for i in range(3) for j in 'abc']
[[0, 'a'], [0, 'b'], [0, 'c'], [1, 'a'], [1, 'b'], [1, 'c'], [2, 'a'], [2, 
'b'], [2, 'c']]

And also, a fourth case for completeness:

 >>> [[i,j] for i in range(3) for j in 'abc',]
[[0, 'abc'], [1, 'abc'], [2, 'abc']]

So it seems that the idiom

   for i in range(x),

with the comma right after the for clause, "reduces" the iterated list to 
the original list again, and then apply it to all further iterations of the 
list comprehension. Now, I don't know if this is by design or by accident; 
all I know is that this is something that may be exploited as a useful 
idiom. For instance, neither map or zip have this behavior, of applying the 
same list to all members of the other.

# zip stops at the shortest list
 >>> zip([[0,1,2,3,4,5]], 'abc')
[([0, 1, 2, 3, 4, 5], 'a')]

# map fills with none
 >>> map(None, [[0,1,2,3,4,5]], 'abc')
[([0, 1, 2, 3, 4, 5], 'a'), (None, 'b'), (None, 'c')]

# the list comprehension repeats the same value all over
 >>> [[i,j] for i in range(6), for j in 'abc']
[[[0, 1, 2, 3, 4, 5], 'a'], [[0, 1, 2, 3, 4, 5], 'b'], [[0, 1, 2, 3, 4, 5], 
'c']]


There are other ways to make it work with either map or zip, but I think 
it's a good example.


Carlos Ribeiro






More information about the Python-list mailing list