Twenty years later, I wake up

Posted on

generator

Let’s start with list generation

 

You can generate a regular list through a simple formula

What happens if you replace [] with ()?

 

See that x stores an address instead of a list, and this address is the address of our generator object

What’s the use of this thing? Of course, save memory

Assuming that there is a huge set of data to be processed now, it seems impossible to load it into memory once and then process it. This shows the advantages of the generator, because it only occupies the memory space of one data, when it needs to access the next

In data processing, the current data will be overwritten, so it doesn’t matter how much data there is. It can be processed. You can access the next data through the next () or \\\\\\\\.

Of course, we still need to use the loop to access the elements. It’s impossible to type one million next() for 100W data.

 

 

Of course, what if the data can’t be expressed in an expression? The answer is to use function + yield keyword. A function with yield keyword is a generator.

A chestnut (print Fibonacci Series):

 

Yield a can be understood as returning an a, but the current code location will be recorded, and the code will be executed from the next sentence of yield a next time. Take this code for example, starting with the last loop.

1. The next () method starts the generator, which will execute once

2. Program enters wire cycle

3. Return a value when meeting yield a and make several breakpoints

4. Print statement of for loop prints a = 1 by the value of a

5. For continues the loop. If the next() method is called, the generator starts again

6. The generator finds the location of the last breakpoint to execute the code (a, B = B, a + b)

7. Run into yield statement again, return to step 3

……

In addition to the next () method, send () can start the generator, but send can pass a value to the generator, which will force the return value at the last breakpoint to be replaced

 

See that the parameter passed in by send replaces the value of res, not the value of a!!! As for why ‘none’ is printed, in fact, next will pass in a none by default, so when next() is called, none will be printed, while send

Print the parameters passed in by sned.

Finally, a classic producer consumer question

 

 import time
 def consumer(name):
     print("%s is ready to consume" % name)
     while True:
         res = yield
         print("%s has consumed goods %d" % (name,res))
 def producer(name):
     print("%s is ready to produce" % name)
     while True:
         time.sleep(3)
         succ = yield 
         print("produce goods %d and goods %d successfully" % (succ,succ+1))
 c1 = consumer('c1')
 c2 = consumer('c2')
 c1.__next__()
 c2.__next__()
 p1 = producer('p1')
 p1.__next__()
 for i in range(10):
     p1.send(i+1)
     c1.send(i+1)
     c2.send(i+2)

Leave a Reply

Your email address will not be published.