What does "yield" do in a Python function?

In the code below we are creating and using a generator.

# Create a generator
def produce_generator(mylist):
    for item in mylist:
        # This makes this function a generator
        yield item 
# Instantiate the generator
mygenerator = produce_generator([1,2,3])
# Use the generator by yielding its values

Notice the produce_generator function in the above code. That function returns a generator. In other words, the output of produce_generator([1,2,3])is a generator. A function can output a generator only when you use a yield instead of a return keyword. Note that you can also use a for-loop to access the items of the generator:

for item in mygenerator:

Again, you would get 1, 2, and 3 as output.

So, why use a generator anyway when you can use a list and a for-loop?

For two reasons:

1. A generator is a special list-like object with a special skill. It can yield its items on-demand. The on-demand item accessing is made possible through the next( function. So, next is a function that gets a generator as input and returns the next item of the generator. So, when you call next for the first time, you get the first item; when you call it the second time (inside the same script or session), you get the second item and so on until the generator is exhausted. That can become useful in special code scenarios. 

2. Generators are memory efficient. Let's say you have a big file that you want to read. It would be more memory efficient to loop over a generator than a list:

def read_csv(file):
    for line in open(file, 'r'):
        yield line
mygenerator = read_csv('myfile.csv')
for item in mygenerator:

So, even though it feels more intuitive to just open the file and use a for-loop to iterate and print, it is more memory-efficient to create a function that uses yield, and then loop over the output of that function,

Recommended Course

Learn Flask development and learn to build cool apps with our premium Python course on Udemy.