# PEP 255: Simple Generators

David Eppstein eppstein at ics.uci.edu
Wed Jun 20 19:49:33 EDT 2001

```I wrote:
> > I'm wondering if it wouldn't make sense to allow a non-empty return
> > statement in a generator, with the semantics that the object being returned
> > is itself some kind of iterator that is used to continue the sequence.
> >
> > i.e.
> >     def integers(i):
> >         yield i
> >         return integers(i+1)

jeff at ccvcorp.com (Jeff Shannon) replied:

> It seems to me that this would be better written as
>
> def integers(i):
>     while 1:
>         yield i
>         i += 1
>
> but I confess that I don't see offhand how either case generalizes to a
> less-contrived example.  It doesn't *seem* to me that your proposal adds
> significant functionality...  but I'm not so familiar with functional
> programming, so I'm likely missing something.   :)

Ok, another mathematical one:

def collatz(i):
yield i
if i % 2 == 0:
return collatz(i/2)
else:
return collatz(3*i+1)

Yes, of course, you could do it with a loop.  You can do anything with a
loop, so what need is there for recursion or any other such programming
language feature?  But I think the functional point of view is more clearly
expressed here than with a loop.

Second example, more data-structural: since list comparison is
lexicographic, max(x,y) where x and y are two lists should be well-defined.
What about when x and y are not lists but some other kind of iterator?

def maxgen(x,y):
for pair in zip(x,y):
yield max(pair[0],pair[1])
if pair[0] > pair[1]:
return x
elif pair[1] > pair[0]:
return y

(Note this is proof of concept rather than a good implementation, zip is
only supposed to work for lists and this code doesn't deal with the issue
of what happens if you get to the end of one iterator before deciding who
wins.)  Again, you could do this by replacing each of the return stmts with
a loop, but I think this is clearer.

Finally, some earlier messages in this thread requested a way to use the
return statement to yield one last item and then stop.  That is, to
abbreviate the idiom

yield x
return

Here's a way to do it with this definition of a nonempty generator return:

return (x,)
--
David Eppstein       UC Irvine Dept. of Information & Computer Science
eppstein at ics.uci.edu http://www.ics.uci.edu/~eppstein/

```