Scala集合的内存管理如何工作?

时间:2015-09-25 22:02:35

标签: scala scala-collections

我无法弄清楚Scala的不可变序列的某些操作的实现。我将以此为例:

def example: List[Int] = {
  val list0 = List.range(1,10)

  list0.tail
}

一旦函数完成执行,list0现在已超出范围。将list0的头部从内存中删除,或者list0保持不变,直到整个列表被垃圾收集?

2 个答案:

答案 0 :(得分:6)

在您的示例中,list0的头部将留给垃圾收集器进行收集,因为没有任何内容可以引用它。但是,在退出函数时,剩余的项目(尾部)将继续存在(假设呼叫的结果被分配给某些东西)。

列表中的每个单元格都会保留对列表中下一个单元格(或Nil)的引用,但不是反之亦然。

答案 1 :(得分:1)

您正在创建总共12个(可能的)实体

  1. list0 - 包含1到10的列表。
  2. 1到10范围内的10个单独元素。这些元素可能会被实习,但这是一个不同的讨论。
  3. 包含元素2-10的返回值list0.tail
  4. 以下是最后一个大括号之前的概念性记忆图,这里是参考

              Somewhere on JVM Stack list0(head)->1->2 ... ->10
                                                     |
    Top of JVM Stack, contains returnList with head->| 
    

    当函数完成时,将弹出引用list0,并且有资格进行垃圾回收。由于list0是唯一引用1的内容,1也是垃圾收集的公平游戏。

    元素2-10以及包含它们的返回列表将保留在堆上,因为正在运行的代码仍然可以访问引用example的任何人。

    希望这有帮助。