python - 聪明的基于流的 python 程序不会遇到无限递归

标签 python recursion stream infinite lazy-sequences

我正在尝试用巧妙的方法为序列 A003602 创建一个 python 生成器

这似乎有效,但我不明白为什么。在我看来它应该达到无限递归。 python 是否在我不认识的地方进行了一些惰性评估?

def N():
    i=1
    while True:
        yield i
        i+=1

def interleave(a,b):
    def result():
        x=a()
        y=b()
        while True:
            yield next(x)
            yield next(y)
    return result

def RZ():
    return interleave(N,RZ)()

gen=RZ()

对我来说,似乎因为 RZ 立即调用 interleave 返回的方法,而 interleave 又调用 b,它是 RZ(在第一次调用 yield 之前),这应该是无限递归。但这实际上似乎有效。谁能解释一下为什么?

最佳答案

生成器(任何带有 yield 语句的函数)都是惰性的。这意味着 result() 不会开始处理,直到您向它请求第一个值,而您并没有这样做。

这里的根本原因是您首先从 x 中请求一个值。这意味着生成器永远不会询问它的子生成器,直到至少请求第二个值。考虑更简单的例子:

def test():
    yield 1
    a = test()
    while True:
        yield next(a)

a = test()
for i in range(10):
    print(next(a))

这和你的一样有效。它具有无限递归的潜力,但只有在您要求那么多值时才会走那么远。您所要做的就是删除 yield 1 以获得预期的行为。在您的代码中,只需切换 NRZ 并询问下一个值 - 您将获得预期的递归。

关于python - 聪明的基于流的 python 程序不会遇到无限递归,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11068279/

相关文章:

python - 使用乘法运算符在 Python 中定义列表

java - run() 方法中的递归函数?

python - 使用python递归打印星号

node.js 如何实时流式传输 22GB gzipped 文件解压缩

flutter - 如何在 Flutter Cubit 中使用 StreamSubscription

python - 在 Python 中随机改组字典

python - Pdftron - 创建与现有元素具有相同样式的新元素

python - 在Python中解析log4j

java - 使用递归对数字进行阶乘

C:从文件中读取SUB字符