如何以内存有效的方式使用Kotlin的序列和lambdas

时间:2019-10-09 15:41:53

标签: kotlin lambda sequence memory-footprint

因此,我正在编写一些代码,这些代码必须兼具内存效率和快速性。我已经在Java中有了一个可用的参考,但是正在用Kotlin重写它。

我基本上需要加载许多csv文件并将它们加载到树中一次,然后在加载它们之后反复遍历它们。

我最初是使用序列编写整个内容的,但是发现它会导致GC反复出现峰值。

我真的不能分享这段代码,但是想知道你们是否知道会导致这种情况发生的原因。

我很乐意根据需要添加详细信息,但这是我的基本模式。

第1步:inputStream -> csvLines: List<String>

第二步:csvLines.drop(x).fold(emptySequence()) -> callOtherFunctionWithFold -> callOtherFunctionWithFold -> Sequence<OutputObjects>

我将csvLines保留为单独的列表,因为我根据我需要的规则访问特定的行。

第3步:Sequence<OuputObjects> -> nodes

结果是可以使用的,但是与仅使用arraylists并对其进行适当修改的Java等效代码相比,此代码的内存效率和性能却低得多。

查看visualvm输出后,我创建了很多kotlin。*。ArrayIterators。好像我每次使用lamda都创建一个。

那么我该怎么做才能使效率更高?尽管序列应该被延迟地减少对象的创建,但是看起来我在做破坏其能力的事情。

GC运行或总体运行后,序列会重新评估吗?如果是这样,那将使它们不适合在启动时加载的对象中使用,对吧?

visual vm run

1 个答案:

答案 0 :(得分:3)

要使用Kotlin序列,您需要以asSequence()开头

csvLines.asSequence()
    .drop(x)
    .fold(...)
    ...

如果不进行说明,它会使用Collection函数,而是在每个函数之后创建一个新的(中间)集合。