【发布时间】:2016-02-28 17:59:52
【问题描述】:
编写以下程序是为了检查 Scala 中的深度递归在我的机器上的深度。我认为它主要取决于分配给该程序的堆栈大小。然而,在计算出最大递归深度(在出现异常时捕获异常)并尝试模拟此深度的递归后,我得到了奇怪的输出。
object RecursionTest {
def sumArrayRec(elems: Array[Int]) = {
def goFrom(i: Int, size: Int, elms: Array[Int]): Int = {
if (i < size) elms(i) + goFrom(i + 1, size, elms)
else 0
}
goFrom(0, elems.length, elems)
}
def main(args: Array[String]) {
val recDepth = recurseTest(0, 0, Array(1))
println("sumArrayRec = " + sumArrayRec((0 until recDepth).toArray))
}
def recurseTest(i: Int, j: Int, arr: Array[Int]): Int = {
try {
recurseTest(i + 1, j + 1, arr)
} catch { case e: java.lang.StackOverflowError =>
println("Recursion depth on this system is " + i + ".")
i
}
}
}
结果因程序的执行而异。
其中一个是理想的输出:
/usr/lib/jvm/java-8-oracle/bin/java
Recursion depth on this system is 7166.
sumArrayRec = 25672195
Process finished with exit code 0
尽管如此,我得到的第二个可能的输出表明一个错误:
/usr/lib/jvm/java-8-oracle/bin/java
Recursion depth on this system is 8129.
Exception in thread "main" java.lang.StackOverflowError
at RecursionTest$.goFrom$1(lab44.scala:6)
at RecursionTest$.goFrom$1(lab44.scala:6)
at RecursionTest$.goFrom$1(lab44.scala:6)
(...)
at RecursionTest$.goFrom$1(lab44.scala:6)
at RecursionTest$.goFrom$1(lab44.scala:6)
Process finished with exit code 1
我没有观察到它们之间的任何依赖或关系,我只是得到了第一个,其他时候得到了第二个
所有这些都让我想到了以下问题:
- 为什么会出现错误?是什么原因导致的?
- 这是堆栈溢出错误吗,如果是...
- 为什么程序运行时栈的大小会同时变化?有可能吗?
当我将println("sumArrayRec = " + sumArrayRec((0 until recDepth).toArray)) 更改为
println("sumArrayRec = " + sumArrayRec((0 until recDepth - 5000).toArray)),更不用说,行为保持不变。
【问题讨论】:
标签: scala recursion jvm stack-overflow