The following code https://pl.kotl.in/B1ul4rhIP compiles and works in 1.3.72, but fails in 1.4.30, why?
import kotlinx.coroutines.*
sealed class CallResult<out T : Any> {
data class Success<out T : Any>(val data: T) : CallResult<T>()
data class Failure(val error: String) : CallResult<Nothing>()
}
public data class Response<T>(val body: T?)
suspend fun <T : Any> f1(lambda: suspend () -> Response<T>): T = when(val result = f3(lambda())) {
is CallResult.Success -> result.data
is CallResult.Failure -> throw Exception()
}
fun <T : Any> f3(response: Response<T>): CallResult<T> {
val body = response.body
if (body != null) {
return CallResult.Success(body)
} else {
return CallResult.Failure("error")
}
}
fun f4(): Response<Any> {
return Response(Any())
}
fun main() {
GlobalScope.launch {
f1 { f4() }
}
}
Fun fact: this happens only when it is the last call in a lambda (making it a return result), otherwise it compiles also in 1.4:
GlobalScope.launch {
f1 { f4() }
// adding this line makes it compile in 1.4
print("test")
}
GlobalScope.launch
expects lambda whose return type is Unit
, but f1 { f4() }
returns Any
.
@Beholder Are you talking about 1.3.72 or 1.4.30? My question is why one language version compiles and another not…
Besides, I don’t think it is the case since adding <Any>
fixes it:
GlobalScope.launch {
f1<Any> { f4() } // compiles in 1.4.30
}
And, by the way, in the above case the Android Studio incorrectly marks <Any>
as “unnecessary and can be removed”, which is wrong.
1 Like
Kotlin 1.4 switched to a new type-inference. In general the new one is faster and better but with a big change like this there is always the danger of corner cases where the new one is not quite as good (yet). You should probably create an issue at https://kotl.in/issue with your case so this can be fixed in the future.
1 Like
You’re right, the answer to my question is that Kotlin actually switched to a new type inference algorithm in the new version, that explains it. I have created an issue - https://youtrack.jetbrains.com/issue/KT-44889 - hopefully this helps the guys to look into it.
2 Likes
Definitely file a bug. I tried to switch our large codebase form 1.3.72 to 1.4 but there were many issues: code which should compile doesn’t and vice versa — code with obvious errors compiles fine — which is much more problematic. I am waiting on False TYPE_MISMATCH introduced in 1.4 : KT-44831 (jetbrains.com) but there are many more. Until 1.4. gets stable I would advise staying on 1.3.72.