Daniel Pitts
07/06/2024, 6:19 PMclass A
class B
fun make():A = A()
fun make():B = B()
fun main() {
val a:A = make()
val b:B = make()
}Daniel Pitts
07/06/2024, 6:27 PMpackage com.stochastictinkr
class A {
fun configureA() {
println("Configuring A")
}
}
class B {
fun configureB() {
println("Configuring B")
}
}
inline fun make(block: A.() -> Unit = { }): A = A().apply(block)
inline fun make(block: B.() -> Unit = { }): B = B().apply(block)
inline fun accepts(a: () -> A, b: () -> B) {
println(a())
println(b())
}
fun main() {
accepts({ A() }, { B() })
accepts(
{
make {
configureA()
}
},
{
make {
configureB()
}
},
)
}ephemient
07/06/2024, 6:29 PMephemient
07/06/2024, 6:30 PMDaniel Pitts
07/06/2024, 6:31 PMe: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:30:9 Type mismatch: inferred type is Unit but A was expected
e: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:31:13 Overload resolution ambiguity:
public inline fun make(block: A.() -> Unit = ...): A defined in com.stochastictinkr in file Broken.kt
public inline fun make(block: B.() -> Unit = ...): B defined in com.stochastictinkr in file Broken.kt
e: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:32:17 Unresolved reference: configureA
e: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:35:9 Type mismatch: inferred type is Unit but B was expected
e: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:36:13 Overload resolution ambiguity:
public inline fun make(block: A.() -> Unit = ...): A defined in com.stochastictinkr in file Broken.kt
public inline fun make(block: B.() -> Unit = ...): B defined in com.stochastictinkr in file Broken.kt
e: file:///Users/pittsd/dev/RandomStuff/src/main/kotlin/com/stochastictinkr/Broken.kt:37:17 Unresolved reference: configureB
Even when using JvmNameephemient
07/06/2024, 6:31 PMephemient
07/06/2024, 6:32 PMmake(A::configureA) should workDaniel Pitts
07/06/2024, 6:33 PMephemient
07/06/2024, 6:38 PMmake(fun A.() { configureA() })
or giving the arguments different names so you can
make(blockA = { configureA() })
or not using the receiver to disambiguate
make { a: A -> a.configureA() }
changing the signature of make in the latter twoDaniel Pitts
07/06/2024, 6:43 PMDaniel Pitts
07/06/2024, 6:43 PMpackage com.stochastictinkr
class A
class B
class ObjectPool : AutoCloseable {
override fun close() {}
}
inline fun ObjectPool.allocate(configure: A.() -> Unit = { }): A = A().apply(configure)
inline fun ObjectPool.allocate(configure: B.() -> Unit = { }): B = B().apply(configure)
inline fun accepts(a: context(ObjectPool) () -> A, b: context(ObjectPool) () -> B) {
ObjectPool().use { pool ->
println(a(pool))
println(b(pool))
}
}
fun main() {
val existingB: B = B()
accepts(
{
allocate {
}
},
{ existingB },
)
}Daniel Pitts
07/06/2024, 6:45 PMVkPhysicalDeviceMemoryProperties.Buffer and VkAccelerationStructureGeometryMotionTrianglesDataNVDaniel Pitts
07/06/2024, 6:45 PMDaniel Pitts
07/06/2024, 6:49 PMephemient
07/06/2024, 7:02 PMephemient
07/06/2024, 7:03 PMDaniel Pitts
07/06/2024, 7:04 PMephemient
07/06/2024, 7:04 PMephemient
07/06/2024, 7:08 PMThe most popular form of type inference is based on the Hindley-Milner system, which is limited by its lack of support for subtyping. … Hindley-Milner style type inference runs in approximately linear O(n) time for monomorphic code. Cubic biunification by contrast has worst case cubic O(n³) time complexity, hence the name. Subtype based inference is more powerful, but that power comes at a price, as the compiler has to do a lot more work.
ephemient
07/06/2024, 7:09 PMDaniel Pitts
07/06/2024, 7:10 PMephemient
07/06/2024, 7:11 PMDaniel Pitts
07/06/2024, 7:11 PM