Python3 yield explained

Created:

Introduction

We will explain what is the use of the yield keyword in Python3 for beginners. First we will explain some required concepts, like iterators and generators. Then we will explain with a concrete example how to use yield in python. If you feel you already know required concepts, feel free to skip them and go to the yield section.

Required concept 1: Iterators

A collection is a grouping of data items. Any collection can be iterated. Iteration means that each element of the collection is fetched in some order (we don't know the order). In python dict, list, set and tuple are examples of collections.

Let's see an example on how to iterate a list of integers:

import random

def list_of_random(number_of_values):
    res = []
    for _ in range(0, number_of_values):
        # append a random interger to the result
        res.append(random.randint(0, 100))
    return res

for value in list_of_random(10):
    if value > 60:
        # if we foudn a value bigger than 60 print it and exit
        print('Value is {0}'.format(value))
        break

In this example we are doing an iteration on the result of list_of_random(10) function, which returns a list of random integers. It's important to note that list_of_random needs to append the 10 numbers before we can iterate them.

Required concept 2: Generators

Right now we know how to iterate a collection. Suppose we need to iterate list_of_random but instead of ten numbers we need to iterate one millon or more, this will require that the function need to generate 1 million of integers first and also consume more memory to store them. Here is were generators comes to help. In our example generator will reduce the memory usage and will speed up the algorithm since if we found an integer bigger than 60 we don't need to create the list of 1 million integers. Here is the same code as before but using generators. Note that if we used [] in the iteration we were need to wait to generate one million of integers.

import random

for value in (random.randint(0, 100) for _ in range(0, 10000000)):
    if value > 60:
        print('Value is {0}'.format(value))
        break

The yield in Python3 with Examples

We know how to use generators. The yield is like a replacement of the return, except that the function will return a generator. The best way to understand it is with an example:

import random

def list_of_random(number_of_values):
    for _ in range(0, number_of_values):
        yield random.randint(0, 100)

for value in list_of_random(10):
    if value > 60:
        print('Value is {0}'.format(value))
        break

Look at the function list_of_random, we are not appending everything on the list that we used as a result, instead we are doing a yield on each random interger. Sometimes is we can write in one line it's better to use the (), but in more complex function we need to use the yield inside a function. As an optimization tip: if your python application consumes a lot of memory look for collections append, add , etc method and try to replace the return with yields. It is always recommended to iterate collections with the "for" "in".

Remeber that when you call a function that uses yield, the code inside the function will not run. The iteration with "for" "in" executes the code.