Python嵌套生成器异常:为何仅输出4组而非预期16组?
为什么你的生成器只输出4组配对而不是16组?
嘿,这个问题我太熟了!核心原因其实是生成器的"一次性迭代"特性——你大概率在嵌套循环里重复使用了同一个生成器实例,而生成器一旦被遍历完,就再也不会产生新值了。
举个典型的错误写法例子,你可能写了类似这样的代码:
def gen_4_items(): for i in range(4): yield i # 踩坑:复用同一个生成器对象 my_gen = gen_4_items() # 试图用嵌套循环生成4*4=16组配对 result = [(x, y) for x in my_gen for y in my_gen] print(result) # 实际输出:[(0, 0), (0, 1), (0, 2), (0, 3)] 只有4组!
问题出在哪?
当外层循环x in my_gen开始执行时,它并不会一次性把生成器的所有值取完:外层循环第一次拿到x=0后,就进入内层循环y in my_gen,这时候内层循环会把生成器剩下的所有值(0、1、2、3)全部取完,生成4组配对。等内层循环结束回到外层循环时,my_gen已经被彻底耗尽,再也没有新值可以输出,所以外层循环的x再也取不到1、2、3,直接结束,最终就只有4组结果。
怎么修复?
解决方法很简单:每次需要迭代时,都创建一个全新的生成器实例,而不是复用同一个。把上面的代码改成这样:
def gen_4_items(): for i in range(4): yield i # 正确:每次循环都调用函数生成新的生成器 result = [(x, y) for x in gen_4_items() for y in gen_4_items()] print(result) # 这时候就能得到完整的16组配对了!
本质上,生成器是带有状态的迭代器,它的内部指针会随着迭代不断前进,一旦走到末尾就无法回退。所以只要确保每次嵌套迭代都用新的生成器,就能得到你预期的笛卡尔积结果。
内容的提问来源于stack exchange,提问作者Nisba
相关产品推荐
相关产品推荐

