user2836670
user2836670

Reputation: 33

Generators and yield statement

Suppose I want to create a function that takes an iterable. That iterable may contain other iterables to any level. I want to create a function that goes over these in order. So for example:

import collections
def it(l):
  for i in l:
    if isinstance(i, collections.Iterable):
      it(i) 
    else:
      print i


it([ [1, 2, 3], [[4, [5, 6]], 7], 8, [9, 10]])  

This produces the following output (as expected): 1 2 3 4 5 6 7 8 9 10

No supposed I want to do this with a generator. Why doesn't the following work as I would expect it to (essentially replacing the print statement with a yield) :

import collections
def it(l):
  for i in l:
    if isinstance(i, collections.Iterable):
      it(i) 
    else:
      yield i

Thanks!

Upvotes: 3

Views: 97

Answers (1)

mgilson
mgilson

Reputation: 310227

because when you recurse, you return a new generator -- But that generator never yields anything because you don't iterate over it. Instead, do something like:

def it(l):
  for i in l:
    if isinstance(i, collections.Iterable):
      for item in it(i):
        yield item
    else:
      yield i

Or, in python3.3, you can use the yield from keyword.

Upvotes: 5

Related Questions