Reputation: 46938
In Java, Class
has an isAssignableFrom
method defined as follows:
public boolean isAssignableFrom(Class<?> cls)
Determines if the class or interface represented by this
Class
object is either the same as, or is a superclass or superinterface of, the class or interface represented by the specifiedClass
parameter. It returnstrue
if so; otherwise it returnsfalse
. If thisClass
object represents a primitive type, this method returnstrue
if the specifiedClass
parameter is exactly thisClass
object; otherwise it returnsfalse
.Specifically, this method tests whether the type represented by the specified
Class
parameter can be converted to the type represented by thisClass
object via an identity conversion or via a widening reference conversion. See The Java Language Specification, sections 5.1.1 and 5.1.4 , for details.Parameters:
cls
- theClass
object to be checkedReturns:
the
boolean
value indicating whether objects of the typecls
can be assigned to objects of this class
Class
implements the Type
interface. Is there an equivalent isAssignableFrom
method that works on Type
s instead of just Class
es? For example, is there a method that determines if a variable of type List<String>
(which would be represented via an instance of ParameterizedType
) can be assigned to a variable of type List<? extends Object>
?
Upvotes: 8
Views: 5362
Reputation: 8064
There is TypeUtils.isAssignable(Type, Type)
in Apache Commons Lang3
Upvotes: 0
Reputation: 19020
Guava's TypeToken utility provides that functionality. Your query could be answered like this:
// represents List<String>
ParameterizedType stringList = ...;
// represents List<? extends Object>
TypeToken objectList = new TypeToken<List<? extends Object>>(){};
boolean isAssignable = objectList.isAssignableFrom( stringList );
Upvotes: 2
Reputation: 51229
You can cast between any List<...>-s, the protection is weaker than normally.
Try this
List<String> a = new Vector<String>();
List<Integer> b = new Vector<Integer>();
Integer i = new Integer(0);
b.add(2);
a = (List<String>) (Object) b;
System.out.println((Object)a.get(0));
no exceptions will be thrown.
This is because generics are only compile time notion.
If you write
System.out.println(a.get(0));
you will get ClassCastException because println function version determined at compile time will be println(String arg).
Ah, so the answer to the question: it should be incorrect to have such an alternative.
Upvotes: 0
Reputation: 4937
Have a look at javaRuntype -- I've found it useful. It can produce representations of types from instances of java.lang.reflect.Type
, and test assignability between them.
Upvotes: 2