Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Unexpected Type Erasure

I am having an issue with generics and what I presume is type erasure whilst trying to reflect some generic information.

I am using a class based on http://www.artima.com/weblogs/viewpost.jsp?thread=208860 to do the reflection, but that isn't the issue.

The code below demonstrates the issue:

private <U extends MyClass1> U doSomething(MyClass2<U> p) {
     Class<U> classIWant = null;
     for (Class<?> c : GenericTypeUtils.getTypeArguments(MyClass2.class, p.getClass()))      {
        if (MyClass1.class.isAssignableFrom(c)) {
            classIWant = c.asSubclass(MyClass1.class);
            break;
        }
    }
}

Unfortunately the line

classIWant = c.asSubclass(MyClass1.class);

Shows the following error

java: incompatible types
  required: java.lang.Class<U>
  found:    java.lang.Class<capture#4 of ? extends MyClass1>

And that's really confusing me. U extends MyClass1 and therefore U is a MyClass1.

Obviously there is some piece of type erasure I am not understanding here - can anybody help, please. BTW this is Java 1.7.0_40

Thanks

Conrad Winchester

like image 707
Conrad Avatar asked Feb 13 '26 20:02

Conrad


1 Answers

The method asSubclass() is implemented like so

public <U> Class<? extends U> asSubclass(Class<U> clazz) {
    if (clazz.isAssignableFrom(this))
        return (Class<? extends U>) this;
    else
        throw new ClassCastException(this.toString());
}

with a return type of Class<? extends U>. Note, that your U and the U in the asSubclass method are completely unrelated type variables.

So the method asSubclass() returns a value declared with the type Class of some unknown subtype of U, where U in this case is MyClass1.

You are trying to assign this value to a variable of type Class with some known subtype of MyClass1. The compiler can't guarantee that they match and therefore doesn't allow compilation.

You can cast the returned value if you wish, but may end up getting ClassCastException at runtime, if the types don't match.

like image 124
Sotirios Delimanolis Avatar answered Feb 15 '26 08:02

Sotirios Delimanolis



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!