python3-yield生成器

jield的本质是将函数变成一个生成器和迭代器


【例】

import types
from collections import Iterable
#from inspect import isgeneratorfunction

def helloYield(n):
    print("HHHA:0====>")
    for i in range(n):
        print("HHHA:0.1====>")
        n = yield i
        print("HHHA:0.2====>", n)
    print("HHHA:1====>")


print("HHHH:0========>")
yieldReval = helloYield(5)
print("HHHH:1========>")
print("yieldReval is GeneratorType ? : ", isinstance(yieldReval, types.GeneratorType))
print("yieldReval is Iterable ? : ", isinstance(yieldReval, Iterable))
#print("Iterable ? : ", isgeneratorfunction(yieldObj))
print("HHHH:2========>")

for i in yieldReval:
    print("HHHB:0====>i=", i)
    if i == 1:
        print("HHHB:0.1====>send(99)")
        yieldReval.send(99)

输出:

HHHH:0========>
HHHH:1========>  //yieldObj = helloYield(5) //并未调用函数helloYield()
yieldReval is GeneratorType ? :  True       //返回值是一个生成器
yieldReval is Iterable ? :  True            //返回值是一个迭代器
HHHH:2========>        //开始用for 来遍历生成器
HHHA:0====>            //for 循环暂停,helloYield()函数开始执行,
HHHA:0.1====>          //直到遇到“yield"时,helloYield()函数暂停,并将yield后面的值返回给for
HHHB:0====>i= 0        //for 恢复执行,直到本次循环结束或者yieldReval.send()时暂停
HHHA:0.2====> None     //helloYield()函数恢复执行...
HHHA:0.1====>          //直到再遇到yield ...
HHHB:0====>i= 1
HHHB:0.1====>send(99)  //for向helloYield发送数值
HHHA:0.2====> 99       //helloYield()收到数值
HHHA:0.1====>
HHHA:0.2====> None     //(重复上面的过程)...
HHHA:0.1====>
HHHB:0====>i= 3
HHHA:0.2====> None
HHHA:0.1====>
HHHB:0====>i= 4
HHHA:0.2====> None      //直到helloYield()再也无法遇到yield,将抛出StopIteration异常
HHHA:1====>             //for 循环遇到StopIteration异常时结果整个循环体

要点:

1.包含“yield”的函数不再是普通函数,而是一个生成器+迭代器+函数;

2.访问jieldReval时,原执行处的代码与helloYield()函数的代码“交叉执行”;

3.单线程!(两处代码“同时”执行,没有既没有线程切换也没有加锁——这是yield最特别的地方);

参考:https://www.liaoxuefeng.com/article/001373892916170b88313a39f294309970ad53fc6851243000

猜你喜欢

转载自blog.csdn.net/menghaocheng/article/details/83413187