python函数递归调用时对深度没有限制_为什么Python具有最大递归深度?

Python具有最大递归深度,但没有最大迭代深度.为什么递归受限制?像迭代这样处理递归是不是更自然,而不是限制递归调用的数量?

我只想说这个问题的根源来自于尝试实现流(有关流的更多详细信息,请参阅this question).例如,假设我们要编写一个流来生成自然数:

def stream_accum(s, n): # force the stream to a list of length n

def loop(s, acc):

if len(acc) == n:

return acc

hd, tl = s()

return loop(tl, acc + [hd])

return loop(s, [])

def nats():

def loop(n):

return n, lambda: loop(n+1)

return loop(1)

流的递归定义非常吸引人.但是,我想更好/更pythonic的方法是使用发电机.

解决方法:

这里实际上有一些问题.

首先,正如NPE’s answer很好地解释的那样,Python并没有消除尾部调用,因此许多允许在Scheme中进行无限递归的函数在Python中是有限的.

其次,正如NPE所解释的那样,无法消除的调用会占用调用堆栈上的空间.而且,即使在执行TCE的语言中,也有许多递归函数无法像迭代那样对待. (考虑递归调用自身两次的天真Fibonacci函数.)

但是为什么调用堆栈首先是有限的资源? Python堆栈帧至少原则上可以在堆上实现并链接在一起(参见Stackless以获得该原理的存在证明),并且在64位存储器空间中,可以存在超过1000个堆栈帧的空间. (实际上,即使是几乎所有现代平台上的C堆栈都可以容纳超过1000个递归Python解释器调用.)

部分原因是历史性的:股票Python解释器使用固定的C堆栈在您进行递归调用时递归调用自身,并且它最初设计用于32位(甚至24位或20位)平台,其中C堆栈非常小.

但这可能已经改变了,Python 3.0将是一个改变它的完美场所.那么,他们为什么不呢?因为他们做出了有意识的语言设计决定.在Pythonic代码中,递归通常非常浅(例如,遍历浅树结构的os.walk代码);如果你的功能达到1000附近的任何深度,它更可能是一个错误,而不是故意的.所以,限制仍然存在.当然这有点循环 – 如果他们删除了限制(特别是,如果他们消除了尾部调用),更深层次的递归将变得更加惯用.但这就是重点 – 圭多不想要一种语言,其中深度递归是惯用的. (并且大多数Python社区都同意.)

标签:python,recursion,stack

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值