Ich versuche, meinen Hack von einer Antwort auf eine andere question zu verallgemeinern.Eine Kotlin-Util-Funktion schreiben, die eine Selbstreferenz im Initialisierer liefert
Es sollte eine Möglichkeit bieten, einen Wert zu referenzieren, der noch nicht in seinem Initialisierer konstruiert wurde (natürlich nicht direkt, aber in lambdas und Objektausdrücken).
Was ich im Moment haben:
class SelfReference<T>(val initializer: SelfReference<T>.() -> T) {
val self: T by lazy {
inner ?: throw IllegalStateException("Do not use `self` until initialized.")
}
private val inner = initializer()
}
fun <T> selfReference(initializer: SelfReference<T>.() -> T): T {
return SelfReference(initializer).self
}
Es funktioniert, sehen Sie folgendes Beispiel:
class Holder(var x: Int = 0,
val action:() -> Unit)
val h: Holder = selfReference { Holder(0) { self.x++ } }
h.action()
h.action()
println(h.x) //2
Aber an diesem Punkt die Art und Weise, in der initializer
verweist auf den rechnerisch ermittelten Wert ist self
Eigenschaft.
Und meine Frage ist: Gibt es eine Möglichkeit SelfReference
neu zu schreiben, so dass initializer
ein Argument übergeben (oder einen Empfänger) anstelle self
Eigenschaft zu verwenden? Diese Frage kann neu formuliert werden: Gibt es eine Möglichkeit, einen träge bewerteten Empfänger/Argument einer Funktion zu übergeben oder diese Semantik irgendwie zu erreichen?
Was sind die anderen Möglichkeiten, den Code zu verbessern?
UPD: Eine Möglichkeit ist es, eine Funktion zu übergeben, die
self
zurückkehrt, so würde es als
it()
innerhalb der
initializer
verwendet werden. Suche immer noch nach anderen.
Möglicherweise können Sie eine Kombination aus [delegierten Eigenschaften] (https://kotlinglang.org/docs/reference/delegated-properties.html#delegated-properties), [spät initialisierten Eigenschaften] (https://kotlinlang.org/docs/reference/properties.html#late-initialized-properties) und/oder [Inline-Funktionen] (https://kotlinlang.org/docs/reference/inline-functions.html#inline-functions) um dies zu verallgemeinern.Mein Versuch sollte (glaube ich) funktionieren, aber es gibt einen Kotlin-Kompilierungs-Bug, der das jetzt verhindert (siehe https://youtrack.jetbrains.com/issue/KT-10878). – mfulton26