Overloaded function with lambda parameter of different return types

Is there any solution for having several same-named functions for different lambda return types, like the following:

fun execute(code: () -> Int) {} // declaration clash warning
fun execute(code: () -> String) {} // declaration clash warning

Even annotating those functions with @JvmName("executeInt") and @JvmName("executeString") respectively doesn’t help because the call execute{ "ok" } is highlighted with “Overload resolution ambiguity” warning.

And if the answer to the first question is “no”, is it possible to implement this feature in Kotlin?

To my mind, nothing stops the compiler from detecting which version is intended on the call side. As well as nothing stops it from generating type-specific names (like “executeString”) to call from Java that leaves this feature Java-compatible.

PS: Here is the issue. Please feel free to vote.

1 Like

As it seems compiler is not smart enough to figure out types properly, but if you assign lambdas to variables then it works:

@JvmName("executeInt")
private fun execute(code: () -> Int) = println(code())

@JvmName("executeString")
private fun execute(code: () -> String) = println(code())

fun main(args: Array<String>) {
	val intFunction = { 1234 }
	execute(intFunction)
	
	val stringFunction = { "abcd" }
	execute(stringFunction)
}

In my opinion this should be fixed in some future release.

1 Like

The issue about overload resolution ambiguity in this case can be tracked here: https://youtrack.jetbrains.com/issue/KT-11265

1 Like

Thanks. However, I’ve created the more specific issue here https://youtrack.jetbrains.com/issue/KT-22119.
Please feel free to vote.

I tried this just now and it is working for me using kotlin 1.3.41, so I guess it has been fixed, which is nice.

Actually that was a false alarm it does not seem to be working for me after all an I think this would indeed be a great addition to have.