1、Python的最大递归层数是可以设置的,默认的在window上的最大递归层数是998
递归是一个很有用的处理方式,简单到遍历文件夹、处理XML;复杂到人工智能等。
合理使用递归能让我们的程序具有简洁和强的可读性。
默认recursionlimit是1000,可以设置,但设置后也只能跑到四千多,报MemoryError: stack overflow
import sys sys.setrecursionlimit(100000) # 可以通过sys.setrecursionlimit()进行设置,但是一般默认不会超过3925-3929这个范围
# a = sys.getrecursionlimit() # 可以通过来进行获取现在设置的值 # print(a) pass def recursive(n): print(n) n += 1 recursive(n) if __name__ == '__main__': recursive(1)
运行结果:
4731 4732 4733 4734 Traceback (most recent call last): File "E:/D/python/cflcode/testcfl/test_0422_01.py", line 15, in recursive recursive(n) File "E:/D/python/cflcode/testcfl/test_0422_01.py", line 15, in recursive recursive(n) File "E:/D/python/cflcode/testcfl/test_0422_01.py", line 15, in recursive recursive(n) [Previous line repeated 996 more times] File "E:/D/python/cflcode/testcfl/test_0422_01.py", line 13, in recursive print(n) MemoryError: stack overflow Process finished with exit code 1
解决方法:
python的generator,这个是python的一大神器,请参看:http://www.jianshu.com/p/d36746ad845d
def fib(count, cur=0, next_=1): if count <= 1: yield cur else: # Notice that this is the tail-recursive version # of fib. yield fib(count-1, next_, cur + next_) print fib(996)这样我们用关键字Yield代替Return把原来的函数变成了生成器。这样如果你只传入参数解释器是不会真正运行的!!!
#执行结果
<generator object fib at 0x02B00D00>
那我们怎么办呢,这里我们使用的技术称为Trampline,我们用一个方法让它不断执行生成器的next(),达到我们的目的。
import types def tramp(gen, *args, **kwargs): g = gen(*args, **kwargs) while isinstance(g, types.GeneratorType): g=g.next() return g print tramp(fib, 996) #执行结果 3919377061614427623668052985592742430389065042819420493170692719480242247392252775480208752179017313071371501566248877239254299341332131655760767122899079117071192049598939666199865808814650408864891823186505
关于python的最大递归层数详解
在阅读http://www.cnblogs.com/skabyy/p/3451780.html这篇文章的时候,实验yield的流式迭代素数的时候发现有个问题,故详细记录下来。
首先来看看python默认的最大递归层数:
运行环境:Windows 10,x64
python环境:python3.5
1 2 3 4 5 6 7 |
def foo(n):
print (n)
n + = 1
foo(n)
if __name__ = = '__main__' :
foo( 1 )
|
得到的最大数为998,以后就是报错了:RecursionError: maximum recursion depth exceeded while calling a Python object
那么python允许的最大递归层数是多少呢?我们实验下:
import sys sys.setrecursionlimit(100000) def foo(n): print(n) n += 1 foo(n) if __name__ == '__main__': foo(1)
得到的最大数字在3925-3929之间浮动,这个是和计算机有关系的,不然也不会是一个浮动的数字了(数学逻辑讲求严谨)。
我们已经将数字调到足够大了,已经大于系统堆栈,python已经无法支撑到太大的递归了。
对于没有尾递归的编程语言来说,程序运行起来的时候计算机会给当前进程分配栈,每递归一次,计算机就会给当前程序调度一部分来使用,当使用过多了,那么不好意思,我就这么点了。然后,就没有然后了,崩了。python不是尾递归优化的语言,我们不应该使用递归来替代掉循环,循环存在必然有它巨大的意义。递归用于复杂度为O(log(n))的计算是很有意义的,用于O(n)就不怎么好了。
那么有什么好的解决办法呢?当然是有的,比如python的generator,这个是python的一大神器,请参看:http://www.jianshu.com/p/d36746ad845d
总结:
递归是一个很有用的处理方式,简单到遍历文件夹、处理XML;复杂到人工智能等。
合理使用递归能让我们的程序具有简洁和强的可读性。