Why does the second loop over a generator print nothing?
A generator is an iterator, so it can be consumed only once. After the first loop reaches the end, it is exhausted, and later loops or list() calls get no items. Create a new generator, or store the values in a list, to reuse them.
Explain it simply
A generator is like a running Doordarshan serial episode on live TV. Once it has been broadcast, it is gone. A list is a recorded DVD you can replay forever. If you need to watch twice, either record it first (make a list) or ask the channel to start a fresh broadcast (call the generator function again).
Example
def squares(n):
for i in range(n):
yield i * i
gen = squares(4)
print(list(gen)) # Output: [0, 1, 4, 9]
print(list(gen)) # Output: []
total = sum(x for x in squares(4))
print(total) # Output: 14
nums = list(squares(4))
print(max(nums), min(nums)) # Output: 9 0
g = squares(3)
print(next(g), next(g), next(g)) # Output: 0 1 4
try:
next(g)
except StopIteration:
print("exhausted") # Output: exhaustedA classic bug is passing one generator to two functions, such as min(g) and then max(g). The second call sees an empty sequence and raises ValueError.
What to say in the interview
"Generators are one-shot iterators. Once StopIteration is raised, they stay empty. To iterate twice I either call the generator function again to get a fresh one, or materialise the results into a list or tuple, trading memory for reusability."