Was testing the behavior of casting, lists, etc. and ran into something that I can not quite figure out. When casting a list into a list that is not of the same type no exception is thrown, nor when using a safe cast does it result in a null. Why is this?
data class Rectangle(val width: Int, val height: Int)
data class Circle(val radius: Int)
fun main(args: Array<String>) {
val listOfRects: List<Rectangle> = listOf(Rectangle(5,5))
val listOfUnkown: List<Any?> = listOfRects
val listOfWrongType: List<Circle> = listOfUnkown as List<Circle>
// also works, thought should throw null
// val listOfWrongType: List<Circle>? = listOfUnkown as? List<Circle>
print(listOfWrongType)
}
Output
Test.kt:9:44: warning: unchecked cast: List<Any?> to List<Circle>
val listA: List<Circle> = listOfUnkown as List<Circle>
^
[Rectangle(width=5, height=5)]
I also tried making deep copy of the lists when I was setting them just as a sanity check.
The as operator never throws an exception, and if the conversion is not possible, it will return null. Example: In this example, we only have one cast on each block of code, and also this approach allows you to avoid any exceptions that may occur at execution time.
A cast failed when the object that you give is not the good one. Look at this tutorial, it's explain the base.
In Kotlin, the information about actual type arguments of generic types is erased at runtime, and type arguments thus cannot be checked during casts.
That's exactly what an unchecked cast is and what the warning tells you about. You can do such a cast but you have to accept that there is a possible type mismatch at runtime by suppressing the warning.
See the language reference:
Type erasure and generic type checks
Unchecked casts
Related Q&A:
List<Any?>
to List<Waypoint>
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