我有一个程序通过递归传递大量数据,比如1000个变量。递归将至少运行50或60次。我担心的是,是否存在数据被覆盖在内存位置上的可能性,因为没有太多空间,或者如果情况没有内存,我会得到程序内存的异常已经用完了(我没有收到这样的错误)?
是否有可能获得错误的解决方案,因为该程序没有更多的内存并且在现有位置上覆盖?
答案 0 :(得分:15)
涉及两个存储区域:stack和堆。堆栈是保持方法调用的当前状态的地方(即局部变量和引用),堆是存储对象的位置。 The Hotspot documentation表示在Linux 64位上,默认情况下每个线程的堆栈为1024kB。堆可以任意大,今天它的大小是GB。
递归方法同时使用堆栈和堆。你首先用完哪一个取决于实现。例如,考虑一个需要数千个整数的方法:如果它们被声明为局部变量,即:
public void stackOverflow() {
int a_1;
int a_2;
int a_3;
// ...
int a_10_000_000;
}
你的程序将使用StackOverflowError
进行攻击。另一方面,如果在数组中组织整数,例如:
public void outOfMemory() {
int[] integers = new int[10 * 1000 * 1000];
}
堆将很快填满,程序将以OutOfMemoryError
结束。在这两种情况下,内存都已损坏或数据被覆盖。但是,在这两种情况下,代码都是错误,必须以某种方式修复 - 但要告诉您 我们需要了解有关您的计划的更多信息。
答案 1 :(得分:5)
是否有可能将数据覆盖在内存中 位置,因为空间不大
Java将对象存储在堆空间中,这些值仅由垃圾回收器回收。这意味着你传递的是引用而不是函数的值,它不会消耗内存,因为你没有复制变量(但是通过增加堆栈帧来增加内存)。如果在线程堆栈中引用了对象,则无法覆盖它。
[...]或如果案件没有记忆,我会得到一些 程序存储器用完的例外
如果JVM耗尽了内存,你会得到一个Asynchronous exception(OutOfMemoryError)但是如果你的递归函数自称为巨大的,那么唯一的例外是StackOverflowError次数。
答案 2 :(得分:2)
不可能出现错误结果:如果出现堆栈溢出,您的程序将{strong>终止过早地使用StackOverflowError。
存储数据的内存位置不能被其他任何内容覆盖。
答案 3 :(得分:1)
Java甚至就此而言,你的程序内存永远不会改变无关内存的状态。
虽然JVM不支持尾递归。因此,当没有更多可用空间时,您将获得最大值StackOverFlowError。你不应该担心数据损坏,而是看看递归堆栈是否太高(比如2000以上)。如果是这样的话就开始工作
答案 4 :(得分:1)
可能有两种情况
足够的内存,递归完成,你得到了ressult。
没有高难的内存和得到StackOverFlowError并退出程序
由于没有发生的内存覆盖,你不会有错误的结果