Kotlin 流中缓冲区之间的差异

Ali*_*ati 6 android kotlin kotlin-coroutines kotlin-flow

据我所知,Kotlin 流程中有三种类型的缓冲区:Buffer、Conflate 和 CollectLatest,我很难弄清楚这三种终端运算符之间的差异。

flow.buffer().collect{...}
flow.collectLatest{...}
flow.conflate().collect{...}
Run Code Online (Sandbox Code Playgroud)

我很抱歉简洁,但是这些缓冲区之间有什么区别以及我们什么时候应该使用它们?

提前感谢任何帮助。

byl*_*azy 16

通常,发射和收集代码是按顺序运行的,“发射器”在前一个值在某处收集之后发射新值。(“收集”意味着终端操作员的 lambda 已完成)。缓冲允许同时运行发出代码和收集代码。

buffer() 允许发射器在旧值仍在处理时发出新值(并将它们保存在缓冲区中供以后使用)。

collectLatest() 在收集到的每个新值上重新启动其 lambda,即使旧值仍在处理中也是如此。

conflate() 运算符会跳过中间值,这意味着在处理当前值后,收集器仅收集处理前一个值期间收到的最新值(与 buffer(capacity = 1, onBufferOverflow = BufferOverflow.DROP_OLDEST)相同。


小智 5

除了指定缓冲区的确切容量之外,缓冲区实际上还接受与通道相同的参数。

使用 buffer 方法,您可以将参数传递给容量参数,以通过以下方式使用任何类型的 Channel。buffer(capacity = Channel.<Type>)还有一个 onBufferOverflow 参数,可用于进一步自定义您的缓冲区。

文档位于https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/buffer.html#:~:text=documentation%20for%20details.-,Parameters,-capacity描述创建新缓冲区的选项。

关于 Channel 类型的很好的解释可以在 Kotlin 的官方网站上找到:

https://play.kotlinlang.org/hands-on/Introduction%20to%20Coroutines%20and%20Channels/08_Channels

buffer()允许多个协程同时处理发出调用,从而节省时间,而不是按顺序等待每个发出调用。

conflate()相当于buffer(capacity = Channel.CONFLATED)buffer(capacity = 1, onBufferOverflow = BufferOverflow.DROP_OLDEST)

如果发生多个发射调用,它仍然会处理所有这些调用,但只会收集最终的调用。

collectLatest(),在多次发出调用的情况下,将不会处理中间值。

相反,当有新的调用可用时,它会取消每个后续调用;只返回最终结果。在您只需要来自流程的最新调用的情况下,这可以提供最快的处理时间。