2016-02-24 21 views
10

Se provo ad accedere al JavaClass di un tipo generico T il compilatore Kotlin lamenta che T non è un sottotipo di kotlin.AnyKotlin: Generics, la riflessione e la differenza tra il tipo T e T: Qualsiasi

class Foo<T> (val t: T){ 
    val cls = t.javaClass // Error, T is not a subtype of kotlin.Any 
} 

Se si definisce T come sottotipo di Qualsiasi tutto funziona bene.

class Bar<T:Any> (val t: T){ 
    val cls = t.javaClass // OK 
} 

Q1) Se il tipo di'T' non è un sottotipo di'Any' quale classe/classi possono essere un sottotipo di?

Q2) Esiste un javaClass per tutte le istanze di T e in caso affermativo come posso accedervi?

risposta

11

Il valore predefinito generic upper bound non è Any ma Any?.

Ciò implica anche che non è sicuro nulla ottenere un valore da javaClass da un argomento nullable.

Per ottenere un javaClass da un'istanza di tipo generico con Any? limite superiore, è possibile gettarlo ai Any:

val cls = (t as Any).javaClass //unsafe 
val clsOrNull = (t as? Any)?.javaClass //safe 
+1

Una cosa che mi Puzzels se è per questo che ho solo bisogno di lanciare per i tipi generici. Per un generico t 'var clsOfT = t? .javaClass' questo dà un errore di compilazione ma per un tipo regolare' var a: Any? = "A"; var clsOfA = a? .javaClass' questo è ok anche se entrambi hanno il upperbound ': Any?'? –

+1

@TomasKarlsson, +1, sembra una particolarità dei generici di Kotlin. Troverò la risposta. – hotkey

+0

Chiarimento a quanto sopra: 't' è una proprietà di tipo generico' T' –