data class House(var name: String = "House", var door: Door = Door())
data class Door(var name: String = "Door")
fun test() {
val testHouse = House("My house", Door(name = "My door"))
}
How could I get nested property reference nice and safe, ideally like this (this doesn't work though):
val houseDoorName = House::door::name
println(houseDoorName.get(testHouse)) //My door
I figured I could maybe do extension function, something like: House::door.nested(Door::name) but Im stuck with the implementation.
For your hypothetical nested function, try this:
fun <A, B, C> ((A) -> B).nested(getter : (B) -> C) : (A) -> C = { getter(this(it)) }
Now you can do exactly what you asked:
val houseDoorName = House::door.nested(Door::name)
val house = House(door = Door(name = "My door"))
println(houseDoorName(house)) // prints "My door"
You can chain it, too:
val doorNameLength = House::door.nested(Door::name).nested(String::length)
The neat trick here is the way Kotlin allows a property reference to be treated as a function.
The nested function is essentially a functional composition. It takes a function a -> b and a function b -> c, and composes them into a new function a -> c. You'll often find it called compose in standard libraries.
Kotlin doesn't have function composition as standard, but there are libraries out there if you need anything more complex than this.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With