Should the compiler throw or at least warn in this...
# compiler
n
Should the compiler throw or at least warn in this case?
Copy code
val list: List<Pair<String, Any>> = …
val doubles = list.filterIsInstance<Pair<String, Double>>()
filterIsInstance can’t check inner generic types, but this code is clean for both IDE and compiler.
s
Looks like https://youtrack.jetbrains.com/issue/KT-29565 was closed as “working as designed” 😞. There’s an open ticket to add an IDE warning, though: https://youtrack.jetbrains.com/issue/KTIJ-16774
n
Nice to know, thanks Sam. Though it should be an error IMO, it’s code that in no case will do what you intended to…
I almost committed it, while refactoring a List<Any> to List<Pair>. Then saw no warning and thought there’s no way this works, and had to open kotlin playground for a sanity check. Very dangerous.
s
I think I agree, it shouldn’t compile without warnings when there’s no way it can actually work at runtime
Copy code
val s = "Hello, World"
val i1: Int = s as Int // warning: "This cast can never succeed"
val i2: Int = s.unsafeCast() // does the same thing, but with no warning 🤦

fun <A, B> A.unsafeCast(): B =
    listOf(Pair(this, null)).filterIsInstance<Pair<B, Nothing?>>().single().first
e
that can't be a global rule but would have to be specific to certain "known" cases only
n
The global rule would be to warn/fail if someone calls
instance is ReifiedTypeWithGenerics
I think… Just like I get a warning if I do listOfInts is List<String>
e
the compiler doesn't see a
instance is ReifiedTypeWithGenerics
in your case though, it sees a
.inlineFunctionCall<ReifiedTypeWithGenerics>()
, which may (or may not) be safe
n
Yeah well I don’t know the compiler internals, but filterIsInstance does this dangerous
is
check and since the function is inlined, it’s probably possible to report the warning/error when I compile my code with it
e
inlining happens pretty late in the compiler, not during frontend AFAIK. but also there's a
is
check in my safe variant as well, that's not something you can warn on
I think it is a good feature request that there should be an unchecked cast warning on
.filterIsInstance<>()
, I just don't think it can be a general rule but can only be on specific known functions