使用 yield 语句的意外输出

问题描述

我现在阅读了 return 和 yield 语句之间的区别并理解了所有内容,当我应用一些测试时,我遵循的教程说有 3 个选项我可以使用它通过 yield 获得结果,其中之一是下一个方法,如您所知,要使用下一个方法,您应该通过多次添加手动创建它,我所做的测试是:

第一种情况:

def test(n):
    yield n*n

def getSquare(n):
    for i in range(n):
        for x in test(i):
            yield x

sq = getSquare(10)
for i in sq:
    print(i)

这里的预期结果是:

0
1
4
9
16
25
36
49
64
81

它按预期工作正常

第二种情况:

def test(n):
    yield n*n

def getSquare(n):
    for i in range(n):
        for x in test(i):
            yield x

sq = getSquare(10)
for i in sq:
    print(next(sq))

因此,我没有多次打印 next(sq),而是将其放入循环中并使用了一次,因此它应该打印出与第一个函数相同的结果,而是打印出该结果:

1
9
25
49
81

我运行了调试,但我无法理解到底发生了什么

解决方法

您在 for 循环中让步,然后立即使用 next() 再次让步

def test(n):
    yield n*n

def getSquare(n):
    for i in range(n):
        for x in test(i):
            yield x

sq = getSquare(10)
for i in sq:
    print("Before next: ",i)
    print("After next:  ",next(sq))

输出:

Before next:  0
After next:   1
Before next:  4
After next:   9
Before next:  16
After next:   25
Before next:  36
After next:   49
Before next:  64
After next:   81
,

代码 for i in sq: 连续迭代迭代器的每个值,但在每次迭代时,您显式调用 next 以获取下一个,您忘记了 i 中的值并继续前进,所以你打印一个超过 2 的值

sq = getSquare(10)
for i in sq:
    print("current ",i)
    print("next:   ",next(sq))


current  0
next:    1
current  4
next:    9
current  16
next:    25
current  36
next:    49
current  64
next:    81

要仅使用 next 在迭代器上移动,请像这样使用并包裹一个 try 来处理 StopIteration 错误

sq = getSquare(10)
try:
    while True:
        i = next(sq)
        print("current ",i)
except StopIteration:
    print("End")