如何避免递归算法中的堆栈溢出?

时间:2018-12-06 01:03:24

标签: algorithm recursion

由于潜在的堆栈溢出问题,我曾经认为迭代算法总是优于递归算法,只要人们不介意在编码上付出额外的努力即可。因此,如果我要构建一个反复使用的util函数,则应该始终进行迭代。这种逻辑正确吗?还是有任何标准技巧可以避免即使很大的N也可以避免递归堆栈溢出?仍然假设数据结构本身不太大,无法放入RAM。

1 个答案:

答案 0 :(得分:0)

基本上,您对普通编译器是正确的,迭代在内存消耗和性能上都优越,但是不要忘记,有一些通常专注于函数式编程和/或AI的语言已针对递归进行了优化,而递归则具有更高的优势。 ..

无论如何,出于您提到的原因,我总是可以使用迭代。但是,递归方法通常比迭代方法更简单,并且转换为迭代所需的编码量太多...在这种情况下,您可以执行以下操作:

  1. 限制堆/堆栈垃圾

    只要每次递归都将对其进行复制/实例化,就可以尽可能地摆脱尽可能多的操作数,返回值和局部变量...

    您可以将static变量用于局部变量,甚至将全局变量用于操作数,但请注意不要通过使用此变量破坏功能。

    您不相信我看到多少次将数组作为操作数传递给递归...

  2. 限制递归

    如果您有多个拆分递归(一个递归层具有多个递归调用),则可以拥有一些内部全局计数器,当前有多少个递归处于活动状态... 如果您达到某个阈值,则不再使用递归调用...而是将它们调度到某个称为优先级队列的全局数组/列表IIRC中,一旦所有挂起的递归停止,就对该队列进行处理,直到其为空。但是,这种方法并不总是适用。这种方法的很好的例子是:洪水填充,网格A *路径查找,...

  3. 增加堆/堆栈大小

    可执行文件具有一个表,该表告诉操作系统为其部分分配多少内存...因此只需在编译器/链接器/ IDE中找到设置,并将其值设置为合理的大小即可。

我确定还有更多的技术,但是这些是我使用的技术...