我们为什么要用 flow?
Posted River_ly
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了我们为什么要用 flow?相关的知识,希望对你有一定的参考价值。
作者:不近视的猫链接
前言
首先,我们得明确 flow 的适用场景,那便是类似播报机情况,每隔一段时间就播报一段相似的内容。由此,假如我们不使用 flow 的情况下,那我们怎么解决这种问题?
- List ❎
- sequence ❎
为什么这么快否决它们?因为他们都是阻塞式的,每两个元素间隔的时间,都会阻塞相应的线程,所以就不过多进行说明。 而另外两个选项可以实现 flow 的效果,也就是可挂起式运行。
- 回调
- LiveData
回调
class MainActivity : AppCompatActivity()
override fun onCreate(savedInstanceState: Bundle?)
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
startDownloading result -> println(result)
private fun startDownloading(callBack: (String) -> Unit)
GlobalScope.launch(Dispatchers.IO)
callBack("开始下载")
delay(100)
callBack("进度为 33%")
delay(100)
callBack("进度为 66%")
delay(100)
callBack("进度为 100%")
delay(100)
callBack("下载完成")
日志输出:
I/System.out: 开始下载
I/System.out: 进度为 33%
I/System.out: 进度为 66%
I/System.out: 进度为 100%
I/System.out: 下载完成
LiveData
class MainActivity : AppCompatActivity()
val result = MutableLiveData<String>()
override fun onCreate(savedInstanceState: Bundle?)
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
result.observe(this) result ->
println(result)
startDownloading()
private fun startDownloading()
GlobalScope.launch(Dispatchers.IO)
result.postValue("开始下载")
delay(100)
result.postValue("进度为 33%")
delay(100)
result.postValue("进度为 66%")
delay(100)
result.postValue("进度为 100%")
delay(100)
result.postValue("下载完成")
日志输出:
I/System.out: 开始下载
I/System.out: 进度为 33%
I/System.out: 进度为 66%
I/System.out: 进度为 100%
I/System.out: 下载完成
总结
em…回调,也就是观察者模式的代表,确实是可以实现类似的效果,同时,LiveData 也是可以实现相应的效果的。
另外,从声明周期的角度来看,回调的方式和 flow 的方式默认都是不支持声明周期结束时自动取消的,而 LiveData 是支持的。
这里我们来验证下 flow 默认有没有自动取消的机制:
class MainActivity : AppCompatActivity()
override fun onCreate(savedInstanceState: Bundle?)
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
GlobalScope.launch
flow delay(8000)
emit(1).collect value ->
println("value -> $value")
override fun onDestroy()
super.onDestroy()
println("onDestroy 已被执行")
结果输出:
I/System.out: onDestroy 已被执行
I/System.out: value -> 1
em…这样看,那岂不是 LiveData 更胜一筹?那我们为什么还要用 flow,干脆直接用 LiveData 就算了?
当然,LiveData 是不能替代 flow 的,因为他们原本就是不同赛道的东西,只不过碰巧 LiveData 能够实现这种异步刷新的功能而已。
另外,正如为什么之前 Rx 系列这么火的原因?并不是他们 Rx 系列能够提供类似回调的功能,而是他们拥有众多操作符,能够非常方便实现各种功能,而 flow 同样有这个优势。
现在 协程+ flow 正在不断取代 Rx 系列的位置,成为主流。从未来的发展角度来看,学习 flow 同样是一种趋势。
总结原因:
- 支持挂起,能够协程进行完美交互
- 拥有众多操作符,能够方便完成各项功能
- Kotlin + flow 成为未来的发展趋势
以上是关于我们为什么要用 flow?的主要内容,如果未能解决你的问题,请参考以下文章