Kotlin
Delegierte Eigenschaften
Suche…
Einführung
Kotlin kann die Implementierung einer Eigenschaft an ein Handler-Objekt delegieren. Einige Standard-Handler sind enthalten, z. B. Lazy-Initialisierung oder beobachtbare Eigenschaften. Es können auch benutzerdefinierte Handler erstellt werden.
Faule Initialisierung
val foo : Int by lazy { 1 + 1 }
println(foo)
Das Beispiel druckt 2
.
Beobachtbare Eigenschaften
var foo : Int by Delegates.observable("1") { property, oldValue, newValue ->
println("${property.name} was changed from $oldValue to $newValue")
}
foo = 2
Die Beispieldrucke foo was changed from 1 to 2
Kartenunterstützte Eigenschaften
val map = mapOf("foo" to 1)
val foo : String by map
println(foo)
Das Beispiel druckt 1
Kundenspezifische Delegation
class MyDelegate {
operator fun getValue(owner: Any?, property: KProperty<*>): String {
return "Delegated value"
}
}
val foo : String by MyDelegate()
println(foo)
Das Beispiel druckt einen Delegated value
Delegat Kann als Schicht verwendet werden, um die Boilerplate zu reduzieren
Betrachten Sie das Null-Typ-System von Kotlin und WeakReference<T>
.
WeakReference
wir also an, wir müssen eine Art Referenz speichern und wir wollten Speicherlecks vermeiden. Hier kommt WeakReference
ins WeakReference
.
Nehmen Sie zum Beispiel folgendes:
class MyMemoryExpensiveClass {
companion object {
var reference: WeakReference<MyMemoryExpensiveClass>? = null
fun doWithReference(block: (MyMemoryExpensiveClass) -> Unit) {
reference?.let {
it.get()?.let(block)
}
}
}
init {
reference = WeakReference(this)
}
}
Nun ist dies nur mit einer WeakReference. Um diese Boilerplate zu reduzieren, können wir einen benutzerdefinierten Eigenschaftsdelegierten verwenden, der uns wie folgt hilft:
class WeakReferenceDelegate<T>(initialValue: T? = null) : ReadWriteProperty<Any, T?> {
var reference = WeakReference(initialValue)
private set
override fun getValue(thisRef: Any, property: KProperty<*>): T? = reference.get()
override fun setValue(thisRef: Any, property: KProperty<*>, value: T?) {
reference = WeakReference(value)
}
}
Jetzt können wir Variablen verwenden, die mit WeakReference
wie normale, nullfähige Variablen WeakReference
sind!
class MyMemoryExpensiveClass {
companion object {
var reference: MyMemoryExpensiveClass? by WeakReferenceDelegate<MyMemoryExpensiveClass>()
fun doWithReference(block: (MyMemoryExpensiveClass) -> Unit) {
reference?.let(block)
}
}
init {
reference = this
}
}