0

I just spent two hours chasing a bug down and realized it was due to this odd behavior. Why does iterating through a Python zip object also empties it? Sometimes I want to print(list(zip)) for debug purposes while not changing the zip object. Is there a way to do that?

In [11]: a = zip([1,2,3],['one','two','three'])                                                                                                                                               

In [12]: print(list(a))                                                                                                                                 
[(1, 'one'), (2, 'two'), (3, 'three')]

In [13]: print(list(a))                                                                                                                                 
[]
Ilya Voytov
  • 329
  • 1
  • 9
  • No, you'd have to keep your list aroudn, i.e. `a = list(zip(a))`. This behavior isn't odd, btw, it is the same for all iterators, which `zip` objects are, but also `map` and `filter` objects, and generator objects... iterators are a pretty important part of python that you should get a handle on. – juanpa.arrivillaga May 01 '20 at 20:04
  • 1
    Because the `zip` object doesn't store any of the generated tuples. In fact, none of them are generated *until* you iterate over the `zip` object. This was the whole reason for changing `zip` from a function that returned a `list` (as it was in Python 2) into a class. – chepner May 01 '20 at 20:06

1 Answers1

1

zip creates an object for iterating once over the results. This also means it's exhausted after one iteration:

>>> a = [1,2,3]
>>> b = [4,5,6]
>>> z = zip(a,b)
>>> list(z)
[(1, 4), (2, 5), (3, 6)]
>>> list(z)
[]

You need to call zip(a,b) every time you wish to use it or store the list(zip(a,b)) result and use that repeatedly instead.

Taken from here

AzyCrw4282
  • 7,222
  • 5
  • 19
  • 35