Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

getClass() of a Generic Method Parameter in a Java

The following Java method fails to compile:

<T extends Number> void foo(T t)
{
    Class<? extends T> klass = t.getClass();
}

Error received is: Type mismatch: cannot convert from Class<capture#3-of ? extends Number> to Class<? extends T>

Can someone explain why Class<? extends T> is invalid, but Class<? extends Number> is fine?

Javadoc says:

The actual result type is Class<? extends |X|> where |X| is the erasure of the static type of the expression on which getClass is called. For example, no cast is required in this code fragment:

Number n = 0;
Class<? extends Number> c = n.getClass(); 
like image 327
MikeM Avatar asked Sep 01 '11 20:09

MikeM


People also ask

What is a generic parameter in Java?

Generics means parameterized types. The idea is to allow type (Integer, String, … etc., and user-defined types) to be a parameter to methods, classes, and interfaces. Using Generics, it is possible to create classes that work with different data types.

How do I get a class instance of generic type T?

The short answer is, that there is no way to find out the runtime type of generic type parameters in Java. I suggest reading the chapter about type erasure in the Java Tutorial for more details. A popular solution to this is to pass the Class of the type parameter into the constructor of the generic type, e.g.

How many type parameters can be used in a generic class?

You can also use more than one type parameter in generics in Java, you just need to pass specify another type parameter in the angle brackets separated by comma.


1 Answers

Because the T class' type doesn't extend from T. Instead, it extends from Number, exactly as you have declared yourself in <T extends Number>. Simple as that.

A better question would be:

Why doesn't the following compile?

<T extends Number> void foo(T t)
{
    Class<T> class1 = t.getClass();
}

The answer to that is that the Object#getClass() returns Class<?> with an unbounded wildcard ? because the object itself is not directly aware about its generic type which is been expected in an arbitrary method.

like image 178
BalusC Avatar answered Oct 25 '22 14:10

BalusC