我有一个非常大的数字列表,它经历了大量的数学操作。我只关心最后的结果。要模拟这种行为,请参阅下面的示例代码:斯卡拉的范围和内存问题
object X {
def main(args:Array[String]) = {
val N = 10000000
val x = List(1 to N).flatten
println(x.slice(0,10))
Thread.sleep(5000)
val y = x.map(_*5)
println(y.slice(0,10))
Thread.sleep(5000)
val z = y.map(_+4)
println(z.slice(0,10))
Thread.sleep(5000)
}
}
所以x是一个非常大的列表。我只关心结果z。为了获得z,我首先必须用数学方法处理x来得到y。然后我操纵y得到z。 (我不能一步一步从x到z,因为操作很复杂,这只是一个例子)
所以当我运行这个例子时,内存不足大概是因为x,y和z是都在范围内,他们都占有记忆。
所以我尝试以下方法:
def main(args:Array[String]) = {
val N = 10000000
val z = {
val y = {
val x = List(1 to N).flatten
println(x.slice(0,10))
Thread.sleep(5000)
x
}.map(_*5)
println(y.slice(0,10))
Thread.sleep(5000)
y
}.map(_+4)
println(z.slice(0,10))
Thread.sleep(5000)
}
所以现在只有Z是在范围之内。所以大概x和y被创建,然后当它们超出范围时收集垃圾。但这不是发生的事情。相反,我再次用光了内存!
(注:我用java -Xincgc,但它并不能帮助)
问题:当我有足够的内存只有1大名单,可我不知用操纵它只是VAL的(即没有可变变量或ListBuffers),也许使用范围来强制gc?如果是这样,怎么样? 谢谢
您将始终需要两个列表的内存。出于好奇,你有没有设置你的Java堆?考虑'阵列'? –
没错,我总是需要2个列表的内存,这是我的。 但我不应该需要内存3列表,我没有。 你同意吗? 在任何情况下,由于x和y超出范围,为什么一旦VM发现内存不足并且变量不在范围内,它们就不会被垃圾回收? –