concise and fast zip operation on lists of lists in Python?
-
07-07-2021 - |
Question
Is there a more concise and time efficient way to achieve the following zip
operation in Python? I am pairing lists of lists together to make new lists, as follows:
>>> a
[[1, 2, 3], [4, 5, 6]]
>>> b
[[10, 11, 12], [13, 14, 15]]
>>> for x, y in zip(a, b):
... print zip(*[x, y])
...
[(1, 10), (2, 11), (3, 12)]
[(4, 13), (5, 14), (6, 15)]
thanks.
Solution
I don't really see a better way other than replacing:
print zip(*[x, y])
with:
print zip(x,y)
If you're really working with 2 element lists, you could probably just do:
print zip( a[0], b[0] )
print zip( a[1], b[1] )
(It'll be slightly more efficient as you leave off 1 zip, but I'm not convinced that it is more clear, which is what you should really be worried about).
If you're really into compact code, you can use map
:
map(zip,a,b) #[[(1, 10), (2, 11), (3, 12)], [(4, 13), (5, 14), (6, 15)]]
Which again might be more efficient than the other version, but I think you pay a slight price in code clarity (though others may disagree).
OTHER TIPS
>>> [zip(i, j) for i, j in zip(a,b)]
[[(1, 10), (2, 11), (3, 12)], [(4, 13), (5, 14), (6, 15)]]
Of course, this is really just the same thing that you wrote above.
In addition to what @mgilson said, you can also consider using itertools.izip
if the lists you are zipping are big.
Since izip
computes elements only when requested and only returns an iterator, the memory usage is much less than zip
for large lists.
This works well too:
print zip(sum(a,[]),sum(b,[]))
prints:
[(1, 10), (2, 11), (3, 12), (4, 13), (5, 14), (6, 15)]
This is probably the best performance wise and is concise as well:
from itertools import chain
print zip(chain(*a),chain(*b))
same output