流与视图与迭代器

Scala 中的流、视图(SeqView)和迭代器之间有什么区别:

  • 他们都是懒人。
  • 流缓存值。
  • 迭代器只能使用一次? 您不能回到开始并再次计算值吗?
  • 视图的值没有缓存,但是您可以一次又一次地计算它们吗?

因此,如果我想节省堆空间,我应该使用迭代器(如果我不再遍历列表)还是视图?谢谢。

22521 次浏览

首先,它们都是 不严格。这对函数有特殊的数学意义,但基本上意味着它们是按需计算的,而不是预先计算的。

Stream确实是一个懒惰列表。实际上,在 Scala 中,StreamList,它的 taillazy val。一旦计算出一个值,该值将保持计算并被重用。或者,如您所说,这些值是缓存的。

Iterator只能使用一次,因为它是集合中的 遍历指针遍历指针,而不是集合本身。Scala 的特殊之处在于,您可以应用诸如 mapfilter之类的转换,并且只需获得一个新的 Iterator,它只会在您请求下一个元素时应用这些转换。

Scala 曾经提供可以重置的迭代器,但是很难以一般的方式支持,而且他们没有制作2.8.0版本。

视图的查看方式与数据库视图非常相似。它是一系列应用于集合以产生“虚拟”集合的转换。如您所说,每次需要从中提取元素时,都会重新应用所有转换。

Iterator和视图都具有优秀的内存特性。Stream很不错,但是在 Scala 中,它的主要好处是编写无限序列(特别是递归定义的序列)。一个 可以避免在内存中保留所有的 Stream,但是,通过确保您不保留对它的 head的引用(例如,使用 def而不是 val来定义 Stream)。

由于视图带来的损失,与视图的总体大小相比,通常应该在应用转换之后对其进行 force处理,或者如果预期只获取少量元素,则将其保留为视图。