Python generators

Better than lists (sometimes).

the benefits over lists:

  1. Readability
  2. Performance - doesn’t hold everything in memory. This matters with a lot of stuff.

The list way #

A list-based approach:

def square_numbers(nums):
    result = []
    for i in nums:
        result.append(i*i)
    return result

my_nums = square_numbers([1, 2, 3, 4, 5])

print my_num

The generator way #

A generator-based approach:

def square_numbers(nums):
    for i in nums:
        yield (i*i)

my_nums = square_numbers([1, 2, 3, 4, 5])

print my_num

yield is the key word to make this a generator.

This no longer returns a list; it returns a generator (i.e., <generator object...>)

Why do this at all?

Generators don’t hold the result in memory; it yields one result at a time

Nothing’s been computed, it’s waiting for an ask.

To get the first value:

print next(my_nums)

Then another:

print next(my_nums)

Until there’s nothing left for the generator to provide.

Can also use a for loop:

for num in my_nums:
    print(num)

The list comprehension way #

The previous block could have been written as list comprehension as well.

my_nums = [x*x for x in [1,2,3,4,5]]

Which can be converted into a generator simply by replacing parenthesis with brackets.

my_nums = (x*x for x in [1,2,3,4,5])

for num in my_nums:
    print(num)