最大递归深度误差

时间:2014-01-13 01:25:55

标签: python tail-recursion

我一直在网上搜索,但却找不到任何有用的东西。我正在python中运行一个基本的dfs算法。我的错误出现在explore

dfs子例程中
def dfs(graph):
    for node in graph:
       if not node in visited:
          explore(graph, node)


def explore(graph, v):
   visited.append(v)
   adjNode = graph[v]
   for i in range(0, len(adjNode)):
       if not adjNode[i] in visited:
          explore(graph, adjNode[i])

visited是我用来跟踪被访问节点的列表,而graph是一个包含图表的字典。 标准递归限制为1000我得到此错误

  File "2breakDistance.py", line 45, in explore
    explore(graph, adjNode[i], cycles)
  File "2breakDistance.py", line 45, in explore
    explore(graph, adjNode[i], cycles)
  File "2breakDistance.py", line 45, in explore
    explore(graph, adjNode[i], cycles)
  File "2breakDistance.py", line 45, in explore
    explore(graph, adjNode[i], cycles)
  File "2breakDistance.py", line 41, in explore
    adjNode = graph[v]
RuntimeError: maximum recursion depth exceeded in cmp

首先,我不太清楚为什么错误发生在adjNode = graph[v],因为explore是递归调用而adjNode只是列表赋值。

但是为了处理递归错误,我使用sys.setrecursionlimit(5000)增加了递归限制我不再得到错误,但程序在adjNode = graph[v]行之前退出并退出而没有错误。它甚至没有到达dfs的末尾,所以我不太确定发生了什么。感谢阅读所有这些以及任何帮助!

2 个答案:

答案 0 :(得分:1)

Python不太擅长递归。它不会进行任何尾调用优化,并且除非您手动更改递归限制,否则会很快耗尽帧空间。查找和再次调用函数的速度也慢,而不是在没有递归的情况下将代码保存在循环中。

尝试在不递归的情况下重写此代码。错误可能发生在创建新帧的任何地方,而不仅仅是你的递归调用的位置,这就是错误发生在那里的原因。

答案 1 :(得分:0)

def explore(graph, v):
    visited.append(v)
    adjNode = graph[v]
    for i in range(0, len(adjNode)):
        if not adjNode[i] in visited:
            explore(graph, adjNode[i])

这对我来说没有意义,节点对象中有什么?为什么要将adjNode分配回传入的节点的值。另一个是adjNode是否像“GetConnections()”函数那样调用?

目前的逻辑应该是这样的:

1. For each Node in Nodes:
      2. Add Node to visited
         Get Nodes Connections
         Explore SubNodes: 
             Go to 2.