Funny interaction with reified types and Any upper bound


#1

I'm running into trouble because:

>>> Boolean::class.java == java.lang.Boolean.TYPE

true

but:

>>> inline fun <reified T : Any> reifiedClass () = T::class.java

>>> reifiedClass<Boolean>() == java.lang.Boolean.TYPE

false

>>> reifiedClass<Boolean>() == java.lang.Boolean::class.java

true

Is it intentional that reifying a type results in the boxed type literal being provided rather than the primitive type literal? I was under the assumption that an inline function was equivalent to its expanded code, but in this case it changes things subtly.

Maybe I'm misunderstanding Any, but I believe Any to be a (synthetic) supertype over both value types (Boolean, Int, Long, etc.) and reference types, so by using Any as an upper bound in my inline function, I'm not causing the boxing.


#2

I think there is no ideal choice about whether to use boxing class or primitive, we have chosen that way because we wanted to preserve some common invariants for generics in Java:

 
 
inline fun <reified T : Any> foo(x: T, y: List<T>) {
    assert(T::class.java == x.javaClass && x.javaClass == y[0].javaClass)
}

I.e. we wanted to make T::class.java equal to x.javaClass, and at the same time x should be boxed as in any other generic declaration