java - “合并”数据或“设置”数据,MediatorLiveData
问题描述
文档(https://developer.android.com/reference/androidx/lifecycle/MediatorLiveData)谈论合并数据......但功能显然是设置它。
当我考虑“合并”时,我会想到诸如 .add() 或 .put() 或 .set(X x, Y y),.. 之类的东西,我可以将 2 个对象捆绑在一个中,或者一个列表对象或对象数组。
但是函数说.setValue(),文档说合并
日志给我的印象是前 2 个 setValue() 被完全忽略:
所以不是:
ViewModel: onChnaged: [Folder1, Folder2, Folder3]
Fragment: onChanged: Folder1 ...etc
ViewModel: onChanged: []
Fragment: onChanged:
ViewModel: onChanged: [Quantity1, Quantity2, Quantity3]
Fragment: onChanged: Quantity1 ...etc
只有第一个 .setValue(folders) 显示在 Fragment 上,我猜这只是因为它在 3 个要解决的查询中花费的时间最长。
……
因此,如果我对合并的概念有误,我需要在其中使用 Diff.Util 执行 LiveData/MutableLiveData<List<?>> 来管理传入列表或单个对象以及处理异步时间的信号量( ?也许?)..和一个 .add() 和 .replace() 函数相应地,等等...,但是我可以使用任何 LiveData,而不是 MediatorLiveData<>。
有什么我可以用的吗?
我错过了什么?
最糟糕的是,如果 MediatorLiveData 像我认为的那样做,那么在正确处理其生命周期的同时将多个 LiveData 连接到单个观察者真的不难......重点是什么。
我看到一些使用 .combine(data1, data2) 的 Kotlin 示例,但该函数甚至不存在。
解决方案
这个答案在kotlin,希望你能看懂或者有人能翻译成java。我有这个扩展,它将 3 个 livedata 源组合到一个对象中。
扩大:
fun <T, A, B, C> LiveData<A>.combineAndCompute3(
other1: LiveData<B>,
other2: LiveData<C>,
onChange: (A, B?, C?) -> T
): LiveData<T> {
var source0emitted = false
var source1emitted = false
var source2emitted = false
val result = MediatorLiveData<T>()
val mergeF = {
val source0Value = this.value
val source1Value = other1.value
val source2Value = other2.value
if (source0emitted && source1emitted && source2emitted) {
result.value = onChange.invoke(source0Value!!, source1Value, source2Value)
}
}
result.addSource(this) { source0emitted = true; mergeF.invoke() }
result.addSource(other1) { source1emitted = true; mergeF.invoke() }
result.addSource(other2) { source2emitted = true; mergeF.invoke() }
return result
}
在我的视图模型中,我有这样的:
private val _id = MutableLiveData<Int>()
private val id = _id.distinctUntilChanged()
private val _name = MutableLiveData<String?>()
private val name = _name.distinctUntilChanged()
private val _load = MutableLiveData<Boolean>()
private val load = _load.distinctUntilChanged()
private val detailLoad = id.combineAndCompute3(name, load) {
A, B, C -> DetailLoad(A, B, C)
}
DetailLoad 是一个常规数据类,A 是一个整数,B 是一个字符串,C 是一个布尔值,我以非常标准的方式将值 postValue 到我的 mutablelivedatas 中。
推荐阅读
- encryption - 如何解决 weblogic nodemanger 进程中的 SWEET32 和 Logjam 漏洞
- python - 在 Windows 上的环境变量中包含 DJANGO_SETTINGS_MODULE
- javascript - 如何在 ReactJS 中将二维数组转换为逗号分隔的字符串
- python - 如何在python中读取具有特定标识符的kml文件?
- sql - 如何在 SQL Developer 中编辑 XML 列?
- ios - 为什么我的for循环在viewDidLoad中放不完?
- audio - 如何避免在 Safari 中开始播放音频文件时出现延迟
- eclipse - Eclipse Orion WebIDE 中的 Sap UI 核心库问题
- xml - 使用 XSL 将 XML 从 Get 转换为 AddChange
- c# - “Microsoft.IdentityModel.Tokens, Version=5.6.0.0”和“Microsoft.IdentityModel, Version=3.5.0”中都存在“SecurityTokenDescriptor”类型。