[英]Lazy initialization with repository
I checked out the Android Sunflower best practices app.我查看了Android Sunflower最佳实践应用程序。 And i kinda struggle to understand why the initialization of the PlantDetailsViewModel is working.
我有点难以理解为什么PlantDetailsViewModel的初始化有效。 The class is defined as follows
该类定义如下
class PlantDetailViewModel @AssistedInject constructor(
plantRepository: PlantRepository,
private val gardenPlantingRepository: GardenPlantingRepository,
@Assisted private val plantId: String
) : ViewModel() {
val isPlanted = gardenPlantingRepository.isPlanted(plantId)
val plant = plantRepository.getPlant(plantId)
....
@AssistedInject.Factory
interface AssistedFactory {
fun create(plantId: String): PlantDetailViewModel
}
companion object {
fun provideFactory(
assistedFactory: AssistedFactory,
plantId: String
): ViewModelProvider.Factory = object : ViewModelProvider.Factory {
@Suppress("UNCHECKED_CAST")
override fun <T : ViewModel?> create(modelClass: Class<T>): T {
return assistedFactory.create(plantId) as T
}
}
}
} }
here the gardenPlantingRepository
and plantRepository
give access to a Room Database .在这里,
gardenPlantingRepository
和plantRepository
可以访问Room Database 。 I wonder that this works because normally it is not possible to access a room database on the main thread.我想知道这是否有效,因为通常无法访问主线程上的房间数据库。 The Viemodel is used in the PlantDetailFragment and lazy initialized.
Viemodel 用于PlantDetailFragment并进行延迟初始化。
@Inject
lateinit var plantDetailViewModelFactory: PlantDetailViewModel.AssistedFactory
private val plantDetailViewModel: PlantDetailViewModel by viewModels {
PlantDetailViewModel.provideFactory(
plantDetailViewModelFactory,
args.plantId
)
}
if i try something that is quite the same i always get the problem that it is not possible to access the database on the main thread.如果我尝试一些完全相同的东西,我总是会遇到无法访问主线程上的数据库的问题。 so i tried to init my variables in the
init
function with a coroutine
and Dispatchers.IO
but the problem with this is that when i access member variables of my viewmodel they are not initialized.所以我试图用
coroutine
和Dispatchers.IO
在init
函数中初始化我的变量,但问题是当我访问我的视图模型的成员变量时,它们没有被初始化。 so how is the behaviour of the sunflower app reproducible那么向日葵应用程序的行为如何重现
Repository uses Dao methods that return LiveData Repository 使用返回 LiveData 的 Dao 方法
The Room persistence library supports observable queries, which return LiveData objects.
Room 持久性库支持可观察查询,它返回 LiveData 对象。 Observable queries are written as part of a Database Access Object (DAO).
可观察查询是作为数据库访问对象 (DAO) 的一部分编写的。
Room generates all the necessary code to update the LiveData object when a database is updated.
当数据库更新时,Room 会生成所有必要的代码来更新 LiveData 对象。 The generated code runs the query asynchronously on a background thread when needed.
生成的代码在需要时在后台线程上异步运行查询。 This pattern is useful for keeping the data displayed in a UI in sync with the data stored in a database.
此模式可用于使 UI 中显示的数据与存储在数据库中的数据保持同步。 https://developer.android.com/topic/libraries/architecture/livedata#use_livedata_with_room
https://developer.android.com/topic/libraries/architecture/livedata#use_livedata_with_room
If you want to use coroutines then you should create and expose LiveData
in your ViewModel
如果你想使用协程,那么你应该在你的
ViewModel
创建和公开LiveData
class ViewModel(
val repository: Repository
) : ViewModel() {
private val _liveData = MutableLiveData<SomeType>()
val liveData: LiveData<SomeType> get() = _liveData
init {
viewModelScope.launch(Dispatchers.IO) {
_liveData.postValue(repository.getSomeData())
}
}
}
Then you should observe this liveData in your activity / fragment然后你应该在你的活动/片段中观察这个 liveData
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.