首先简单介绍yield,这里主要参考这篇博客。在Python中,使用yield的函数被称为生成器函数(generator function)。生成器有两种方法:next()和send(),都可以调用生成器。yield和return经常被进行比较,两者差别较大:
我们在定义完一个yield后,在主程序中反复调用几次,分析结果,如下所示:
可以看到,在使用for循环调用时,没有任何问题,第二次调用时,生成器仍然可以输出完整结果。
那如果当数据生成器作为参数,赋予定义的函数中去,又会发生什么呢?继续实验。
可以发现:我们在定义的test1函数中,通过for循环,明明调用了生成器三次,每次都应该输出一遍0,1,2,然而,真实输出结果却只有一次的1,2,3,也就是说,此时,当数据迭代器作为参数赋予定义的函数中时(这种应用场景还是比较多的),在第一个for循环中,正常迭代完成数据生成器。在第二个for循环时,仍然在调用该数据生成器,由于其在上一次已经被迭代完成,所以此时的调用无法生成任何结果!再与在主函数中的运行过程比较,因此,确定该问题的来源!
当发现该问题时,想过很多方法尝试解决,后来发现通过itertools.tee()方法,复制生成器,可以完美解决该问题。具体思路如下:
可以发现,此时,成功通过拷贝数据生成器,完成了在定义函数中对该数据生成器的多次调用。在使用过程中出现了这个问题,且花费较多时间定位到该问题并解决,故记录供参考。