[英]Kotlin lazy usage
I'm currently using Realm in my application, and to make sure i manage Realm instances correctly, i introduced in my base Activity a variable like this: 我目前正在我的应用程序中使用Realm,为了确保我正确管理Realm实例,我在我的基本Activity中引入了一个这样的变量:
protected val realm: Realm by lazy {
Realm.getDefaultInstance()
}
And then in onDestroy i do this: 然后在onDestroy中我这样做:
override fun onDestroy() {
super.onDestroy()
realm.close()
}
And then i realised this is a waste. 然后我意识到这是一种浪费。 If the current activity doesn't use realm, it will open and immediately close in
onDestroy
. 如果当前活动不使用领域,它将打开并立即关闭
onDestroy
。
So i updated to this: 所以我更新到这个:
private var usedRealm = false
protected val realm: Realm by lazy {
usedRealm = true
Realm.getDefaultInstance()
}
override fun onDestroy() {
super.onDestroy()
if (usedRealm) {
realm.close()
}
}
Is there any way to accomplish the same, without the extra flag? 有没有办法完成同样的事情,没有额外的旗帜?
There is a bug in your current implementation. 您当前的实施中存在一个错误。 If
Realm.getDefaultInstance()
throws then usedRealm
will be set to true
but the lazy won't actually be initialized (intialization would have failed). 如果抛出
Realm.getDefaultInstance()
那么usedRealm
将被设置为true
但实际上不会初始化lazy(初始化将失败)。 You can fix this by only calling usedRealm = true
after calling Realm.getDefaultInstance()
: 您可以通过在调用
Realm.getDefaultInstance()
之后仅调用usedRealm = true
来解决此问题:
protected val realm: Realm by lazy { val realm = Realm.getDefaultInstance() usedRealm = true realm }
or 要么
protected val realm: Realm by lazy { Realm.getDefaultInstance().apply { usedRealm = true } }
You can accomplish the same without the extra flag by keeping a reference to the raw Lazy
object itself: 通过保持对原始
Lazy
对象本身的引用,您可以在没有额外标志的情况下完成相同的操作:
private val lazyRealm = lazy { Realm.getDefaultInstance() } protected val realm by lazyRealm override fun onDestroy() { super.onDestroy() if (lazyRealm.isInitialized()) { realm.close() } }
This still requires an additional field but you no longer have to maintain the initialization state yourself. 这仍然需要一个额外的字段,但您不必再自己维护初始化状态。
You can also use Lazy
directly instead of as a delegate : 您也可以直接使用
Lazy
而不是委托 :
protected val lazyRealm = lazy { Realm.getDefaultInstance() } override fun onDestroy() { super.onDestroy() if (lazyRealm.isInitialized()) { lazyRealm.value.close() } }
or 要么
protected val lazyRealm = lazy { Realm.getDefaultInstance() } override fun onDestroy() { super.onDestroy() with(lazyRealm) { if (isInitialized()) { value.close() } } }
This makes it so that there is no extra property but Lazy
is now part of your API and everywhere where you would have simply referenced realm
you now have to reference lazyRealm.value
. 这使得它没有额外的属性,但是
Lazy
现在是你的API的一部分,并且在任何你只想引用它的realm
你现在必须引用lazyRealm.value
。 You get to weigh the pros and cons. 你要权衡利弊。 :-)
:-)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.