Kotlin中asSequence的使用场景

List和Sequence的不同:

1
listOf(1, 2, 3, 4).asSequence().map { it * it }.filter { it > 3 }.toList()

惰性操作存在中间操作和末端操作,如上代码toList()之前的那些就是中间操作,在没有操作toList()之前是没有任何输出和结果的,只是对数据进行加工,最终的计算是在终端操作toList中完成的。Sequence的操作是先对一个元素把所有的操作都加工完,最终在终端操作中进行计算。

1
listOf(1, 2, 3, 4).map { it * it }.filter { it > 3 }

做同样的事情,不用asSequence的话,其中每步操作都会返回一个新的List,然后再对新的List进行操作,每步都是终端操作。

这样就会导致当list有很多元素的时候不加asSequence的时候没进行一个操作都要重新遍历进行操作,导致耗时比较高。

使用场景

  1. 第一个很确定的使用场景是:当处理的元素量很大时,需要使用Sequence,原因已经在上面说了
  2. 对于单一处理步骤,大多数情况下,直接使用List效率更高,Sequence其实不是内联的,当处理多个操作的时候使用Sequence是个好的选择。在这片文章中作者有个例子时只有Map这一个操作的时候Sequence的时间是优于List的
  3. 当使用first或last操作符时,如果再有其他操作的情况下Sequence是最优选择,如果仅有first或last时,应该也是最有选,通过源码可知Sequence的first时iterator.next()而List的first时this[0]。
  4. 当作为参数传递时应该使用List;因为List是存在内存当中,如果把Sequence的当参数可能会多次遍历。

和Java中Stream区别

  1. Kotlin的Sequence更容易使用。
  2. Java的Stream可以使用并行流进行并行操作,我认为这是最主要的一点。

参考文章:

https://juejin.im/post/6844903616072040455

https://juejin.im/post/6844903736364498957

https://juejin.im/post/6844903622409453576

https://juejin.im/post/6844903667947012110