У меня есть очень большой список чисел, которые подвергаются множеству математических манипуляций. Меня интересует только конечный результат. Чтобы смоделировать такое поведение, смотрите мой пример кода ниже:
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'ы (т.е. никаких изменяемых vars или ListBuffers), возможно, используя scoping для принудительного gc? Если да, то как? Спасибо