一个python方法可以无限期地调用自己吗?

问题描述 投票:0回答:2

我有一个python方法,它时常执行一些任务,我发现最简单的方法是写。

class MyClass:
    def a(self):
        #perform the task 
        time.sleep(time_to_sleep)
        self.a()

但是这个方法要运行很长时间 可能要运行几个月 也就是说这个方法可以被递归调用10^4次之多

这样做有什么风险吗?

python tail-recursion
2个回答
6
投票

如果你无限期地在你的函数中不断地递归,你迟早会得到以下错误------。

RuntimeError: maximum recursion depth exceeded

一个简单的例子可以说明这一点 -

>>> def a():
...     global i
...     i += 1
...     a()

然后,我使用-作为运行这个函数

>>> i = 0
>>> a()

这给了我以上的错误,之后当我打印了 i 它是999。所以你迟早会得到这个错误。

你也可以改变这个限制,通过调用 sys.setrecursionlimit() 虽然我不建议这样做,因为你可能会在到达极限之前就炸掉堆栈(一个更简单的方法是使用下面答案中给出的while循环)--------。

import sys
sys.setrecursionlimit(<limit>)

或者你也可以得到- MemoryError - 如果你在本地命名空间中存储了大量的数据,由于你从未真正从递归调用中返回,调用函数的本地命名空间永远不会被清除。因此,你甚至可能在达到最大递归极限之前,就把你的内存炸掉了。


简单的方法是使用while循环,例如-----------------------------------------------。

class MyClass:
    def a(self):
        while True:
            #perform the task 
            time.sleep(time_to_sleep)

4
投票

简而言之:没有! 递归函数是有调用限制的。正如证明,你可以看到自己修改 sys.setrecursionlimit:

import time, sys
# max calls: 3
sys.setrecursionlimit(3)

class MyClass:
    def a(self):        
        print "."
        time.sleep(1)
        self.a()

m = MyClass()
m.a()

当呼叫次数达到3时,你可以看到。RuntimeError:

.
.
Traceback (most recent call last):
  File "teste.py", line 14, in <module>
    m.a()
  File "teste.py", line 11, in a
    self.a()
  File "teste.py", line 11, in a
    self.a()
RuntimeError: maximum recursion depth exceeded

为了方便大家了解,你可以像这样得到递归限制。

>>> import sys
>>> sys.getrecursionlimit()

另外,请注意: 设置一个过高的值并超过sys.getrecursionlimit(),可能会导致C栈溢出,使Python解释器失败。

© www.soinside.com 2019 - 2024. All rights reserved.