public final class Types extends Object
Logic and inspiration were drawn from the following excellent libraries:
com.google.common.reflect
package.org.apache.commons.lang3.reflect
package.
All three of these libraries contain fantastic generics-related logic, but none of the three contained everything that SciJava needed for all its use cases. Hence, we have drawn from sources as needed to create a unified generics API for use from SciJava applications. See in particular the SciJava Ops project, which utilizes these functions heavily.
NB: The
org.apache.commons.reflect.TypeUtils
class of
Apache Commons
Lang version 3.4 is forked internally within this class. We did this for
two reasons: 1) to avoid bringing in the whole of Apache Commons Lang as a
dependency; and 2) to fix an infinite recursion bug in the
TypeUtils.toString(Type)
method.
Modifier and Type | Method and Description |
---|---|
static Map<TypeVariable<?>,Type> |
args(Class<?> c,
ParameterizedType superType)
Tries to determine the type arguments of a class/interface based on a super
parameterized type's type arguments.
|
static Map<TypeVariable<?>,Type> |
args(Type type,
Class<?> toClass)
Gets the type arguments of a class/interface based on a subtype.
|
static Class<?> |
array(Class<?> componentType)
Gets the array class corresponding to the given element type.
|
static Class<?> |
array(Class<?> componentType,
int dim)
Gets the array class corresponding to the given element type and
dimensionality.
|
static Type |
array(Type componentType)
Gets the array type—which might be a
Class or a
GenericArrayType depending on the argument—corresponding to
the given element type. |
static <T> Class<T> |
box(Class<T> type)
Returns the non-primitive
Class closest to the given type. |
static <T> T |
cast(Object src,
Class<T> dest)
Casts the given object to the specified type, or null if the types are
incompatible.
|
static Type |
component(Type type)
Gets the component type of the given array type, or null if not an array.
|
static boolean |
containsTypeVars(Type type)
Learn, recursively, whether any of the type parameters associated with
type are bound to variables. |
static <T> T |
enumValue(String name,
Class<T> dest)
Converts the given string value to an enumeration constant of the specified
type.
|
static Field |
field(Class<?> c,
String name)
Gets the field with the specified name, of the given class, or superclass
thereof.
|
static Type |
fieldType(Field field,
Class<?> type)
Returns the "safe" generic type of the given field, as viewed from the
given type.
|
static boolean |
isAssignable(Type source,
Type target)
Discerns whether it would be legal to assign a reference of type
source to a reference of type target . |
static boolean |
isBoolean(Class<?> type) |
static boolean |
isByte(Class<?> type) |
static boolean |
isCharacter(Class<?> type) |
static boolean |
isDouble(Class<?> type) |
static boolean |
isFloat(Class<?> type) |
static boolean |
isInstance(Object obj,
Class<?> dest)
Checks whether the given object can be cast to the specified type.
|
static boolean |
isInteger(Class<?> type) |
static boolean |
isLong(Class<?> type) |
static boolean |
isNumber(Class<?> type) |
static boolean |
isShort(Class<?> type) |
static boolean |
isText(Class<?> type) |
static Class<?> |
load(String name)
Loads the class with the given name, using the current thread's context
class loader, or null if it cannot be loaded.
|
static Class<?> |
load(String className,
boolean quietly)
Loads the class with the given name, using the current thread's context
class loader.
|
static Class<?> |
load(String name,
ClassLoader classLoader)
Loads the class with the given name, using the specified
ClassLoader , or null if it cannot be loaded. |
static Class<?> |
load(String name,
ClassLoader classLoader,
boolean quietly)
Loads the class with the given name, using the specified
ClassLoader , or null if it cannot be loaded. |
static URL |
location(Class<?> c)
Gets the base location of the given class.
|
static URL |
location(Class<?> c,
boolean quietly)
Gets the base location of the given class.
|
static Method |
method(Class<?> c,
String name,
Class<?>... parameterTypes)
Gets the method with the specified name and argument types, of the given
class, or superclass thereof.
|
static Type[] |
methodParamTypes(Method method,
Class<?> type)
As
fieldType(Field, Class) , but with respect to the parameter
types of the given Method rather than a Field . |
static Type |
methodReturnType(Method method,
Class<?> type)
As
fieldType(Field, Class) , but with respect to the return type of
the given Method rather than a Field . |
static String |
name(Type t)
Gets a string representation of the given type.
|
static <T> T |
nullValue(Class<T> type)
Gets the "null" value for the given type.
|
static Type |
param(Type type,
Class<?> c,
int no)
Gets the given type's
n th type parameter of the specified class. |
static ParameterizedType |
parameterize(Class<?> raw,
Map<TypeVariable<?>,Type> typeArgMappings)
Create a parameterized type instance.
|
static ParameterizedType |
parameterize(Class<?> rawType,
Type... typeArgs)
Creates a new
ParameterizedType of the given class together with
the specified type arguments. |
static ParameterizedType |
parameterizeWithOwner(Type ownerType,
Class<?> rawType,
Type... typeArgs)
Creates a new
ParameterizedType of the given class together with
the specified type arguments. |
static Class<?> |
raw(Type type)
Gets the (first) raw class of the given type.
|
static List<Class<?>> |
raws(Type type)
Gets all raw classes corresponding to the given type.
|
static <T> Class<T> |
unbox(Class<T> type)
Returns the primitive
Class closest to the given type. |
static WildcardType |
wildcard()
Creates a new
WildcardType with no upper or lower bounds (i.e.,
? ). |
static WildcardType |
wildcard(Type[] upperBounds,
Type[] lowerBounds)
Creates a new
WildcardType with the given upper and/or lower
bounds. |
static WildcardType |
wildcard(Type upperBound,
Type lowerBound)
Creates a new
WildcardType with the given upper and/or lower bound. |
public static Class<?> load(String name)
name
- The name of the class to load.load(String, ClassLoader, boolean)
public static Class<?> load(String name, ClassLoader classLoader)
ClassLoader
, or null if it cannot be loaded.name
- The name of the class to load.classLoader
- The class loader with which to load the class; if null,
the current thread's context class loader will be used.load(String, ClassLoader, boolean)
public static Class<?> load(String className, boolean quietly)
className
- the name of the class to load.quietly
- Whether to return null
(rather than throwing
IllegalArgumentException
) if something goes wrong loading
the class.null
if the class could not be loaded
and the quietly
flag is set.IllegalArgumentException
- If the class cannot be loaded and the
quietly
flag is not set.load(String, ClassLoader, boolean)
public static Class<?> load(String name, ClassLoader classLoader, boolean quietly)
ClassLoader
, or null if it cannot be loaded.
This method is capable of parsing several different class name syntaxes. In particular, array classes (including primitives) represented using either square brackets or internal Java array name syntax are supported. Examples:
boolean
is loaded as boolean.class
Z
is loaded as boolean.class
double[]
is loaded as double[].class
string[]
is loaded as java.lang.String.class
[F
is loaded as float[].class
name
- The name of the class to load.classLoader
- The class loader with which to load the class; if null,
the current thread's context class loader will be used.quietly
- Whether to return null
(rather than throwing
IllegalArgumentException
) if something goes wrong loading
the classnull
if the class could not be loaded
and the quietly
flag is set.IllegalArgumentException
- If the class cannot be loaded and the
quietly
flag is not set.public static URL location(Class<?> c)
c
- The class whose location is desired.location(Class, boolean)
public static URL location(Class<?> c, boolean quietly)
If the class is directly on the file system (e.g., "/path/to/my/package/MyClass.class") then it will return the base directory (e.g., "file:/path/to").
If the class is within a JAR file (e.g., "/path/to/my-jar.jar!/my/package/MyClass.class") then it will return the path to the JAR (e.g., "file:/path/to/my-jar.jar").
c
- The class whose location is desired.quietly
- Whether to return null
(rather than throwing
IllegalArgumentException
) if something goes wrong
determining the location.quietly
flag is set.IllegalArgumentException
- If the location cannot be determined and
the quietly
flag is not set.to convert the result to a {@link File}.
public static String name(Type t)
t
- Type whose name is desired.public static Class<?> raw(Type type)
Class
itself, the type itself is returned.
ParameterizedType
, the raw type of the
parameterized type is returned.GenericArrayType
, the returned type is the
corresponding array class. For example: List<Integer>[] => List[]
.
<X extends Foo & Bar> => Foo
.
If you want all raw classes of the given type, use raws(java.lang.reflect.Type)
.
type
- The type from which to discern the (first) raw class.public static List<Class<?>> raws(Type type)
For example, a type parameter A extends Number & Iterable
will
return both Number
and Iterable
as its raw classes.
type
- The type from which to discern the raw classes.raw(java.lang.reflect.Type)
public static boolean isBoolean(Class<?> type)
public static boolean isByte(Class<?> type)
public static boolean isCharacter(Class<?> type)
public static boolean isDouble(Class<?> type)
public static boolean isFloat(Class<?> type)
public static boolean isInteger(Class<?> type)
public static boolean isLong(Class<?> type)
public static boolean isShort(Class<?> type)
public static boolean isNumber(Class<?> type)
public static boolean isText(Class<?> type)
public static <T> Class<T> box(Class<T> type)
Class
closest to the given type.
Specifically, the following type conversions are done:
All other types are unchanged.
public static <T> Class<T> unbox(Class<T> type)
Class
closest to the given type.
Specifically, the following type conversions are done:
All other types are unchanged.
public static <T> T nullValue(Class<T> type)
public static Field field(Class<?> c, String name)
Unlike Class.getField(String)
, this method will return fields of
any visibility, not just public
. And unlike
Class.getDeclaredField(String)
, it will do so recursively,
returning the first field of the given name from the class's superclass
hierarchy.
Note that this method does not guarantee that the returned field is
accessible; if the field is not public
, calling code will need to
use AccessibleObject.setAccessible(boolean)
in order to manipulate the field's
contents.
c
- The class (or subclass thereof) containing the desired field.name
- IllegalArgumentException
- if the specified class does not contain a
method with the given namepublic static Method method(Class<?> c, String name, Class<?>... parameterTypes)
Unlike Class.getMethod(String, Class[])
, this method will return
methods of any visibility, not just public
. And unlike
Class.getDeclaredMethod(String, Class[])
, it will do so
recursively, returning the first method of the given name and argument
types from the class's superclass hierarchy.
Note that this method does not guarantee that the returned method is
accessible; if the method is not public
, calling code will need to
use AccessibleObject.setAccessible(boolean)
in order to invoke the method.
c
- The class (or subclass thereof) containing the desired method.name
- Name of the method.parameterTypes
- Types of the method parameters.IllegalArgumentException
- If the specified class does not contain a
method with the given name and argument types.public static Class<?> array(Class<?> componentType)
For example, arrayType(double.class)
returns double[].class
.
componentType
- The type of elements which the array possessesIllegalArgumentException
- if the type cannot be the component type
of an array (this is the case e.g. for void.class
).public static Class<?> array(Class<?> componentType, int dim)
For example, arrayType(double.class, 2)
returns
double[][].class
.
componentType
- The type of elements which the array possessesdim
- The dimensionality of the arraypublic static Type array(Type componentType)
Class
or a
GenericArrayType
depending on the argument—corresponding to
the given element type.
For example, arrayType(double.class)
returns double[].class
.
componentType
- The type of elements which the array possessescomponent(java.lang.reflect.Type)
public static Type component(Type type)
If you have a Class
, you can call Class.getComponentType()
for a narrower return type.
This is the opposite of array(Type)
.
public static Type fieldType(Field field, Class<?> type)
Field.getGenericType()
returns, if the field is declared in a superclass, or type
has a
type parameter that is used in the type of the field.
For example, suppose we have the following three classes:
public class Thing<T> { public T thing; } public class NumberThing<N extends Number> extends Thing<N> {} public class IntegerThing extends NumberThing<Integer> {}Then this method operates as follows:
field = Types.field(Thing.class, "thing"); field.getType(); // Object field.getGenericType(); // T Types.fieldType(field, Thing.class); // T Types.fieldType(field, NumberThing.class); // N extends Number Types.fieldType(field, IntegerThing.class); // Integer
public static Type methodReturnType(Method method, Class<?> type)
fieldType(Field, Class)
, but with respect to the return type of
the given Method
rather than a Field
.public static Type[] methodParamTypes(Method method, Class<?> type)
fieldType(Field, Class)
, but with respect to the parameter
types of the given Method
rather than a Field
.public static Type param(Type type, Class<?> c, int no)
n
th type parameter of the specified class.
For example, with class StringList implements List<String>
,
Types.param(StringList.class, Collection.class, 0)
returns
String
.
public static boolean isAssignable(Type source, Type target)
source
to a reference of type target
.source
- The type from which assignment is desired.target
- The type to which assignment is desired.NullPointerException
- if target
is null.Class.isAssignableFrom(Class)
public static boolean isInstance(Object obj, Class<?> dest)
cast(Object, Class)
public static <T> T cast(Object src, Class<T> dest)
public static <T> T enumValue(String name, Class<T> dest)
name
- The value to convert.dest
- The type of the enumeration constant.IllegalArgumentException
- if the type is not an enumeration type, or
has no such constant.public static ParameterizedType parameterize(Class<?> rawType, Type... typeArgs)
ParameterizedType
of the given class together with
the specified type arguments.rawType
- The class of the ParameterizedType
.typeArgs
- The type arguments to use in parameterizing it.ParameterizedType
.public static ParameterizedType parameterizeWithOwner(Type ownerType, Class<?> rawType, Type... typeArgs)
ParameterizedType
of the given class together with
the specified type arguments.ownerType
- The owner type of the parameterized class.rawType
- The class of the ParameterizedType
.typeArgs
- The type arguments to use in parameterizing it.ParameterizedType
.public static WildcardType wildcard()
WildcardType
with no upper or lower bounds (i.e.,
?
).WildcardType
.public static WildcardType wildcard(Type upperBound, Type lowerBound)
WildcardType
with the given upper and/or lower bound.upperBound
- Upper bound of the wildcard, or null for none.lowerBound
- Lower bound of the wildcard, or null for none.WildcardType
.public static WildcardType wildcard(Type[] upperBounds, Type[] lowerBounds)
WildcardType
with the given upper and/or lower
bounds.upperBounds
- Upper bounds of the wildcard, or null for none.lowerBounds
- Lower bounds of the wildcard, or null for none.WildcardType
.public static boolean containsTypeVars(Type type)
type
are bound to variables.type
- the type to check for type variablespublic static Map<TypeVariable<?>,Type> args(Type type, Class<?> toClass)
Map
are Object
for the subtype
Properties
even though the subtype does not
directly implement the Map
interface.
This method returns null
if type
is not assignable to
toClass
. It returns an empty map if none of the classes or
interfaces in its inheritance hierarchy specify any type arguments.
A side effect of this method is that it also retrieves the type arguments
for the classes and interfaces that are part of the hierarchy between
type
and toClass
. So with the above example, this method
will also determine that the type arguments for Hashtable
are also both Object
. In cases where the interface
specified by toClass
is (indirectly) implemented more than once
(e.g. where toClass
specifies the interface
Iterable
and type
specifies a
parameterized type that implements both Set
and
Collection
), this method will look at the
inheritance hierarchy of only one of the implementations/subclasses; the
first interface encountered that isn't a subinterface to one of the others
in the type
to toClass
hierarchy.
type
- the type from which to determine the type parameters of
toClass
toClass
- the class whose type parameters are to be determined based
on the subtype type
Map
of the type assignments for the type variables in
each type in the inheritance hierarchy from type
to
toClass
inclusive.public static Map<TypeVariable<?>,Type> args(Class<?> c, ParameterizedType superType)
args(Type, Class)
which gets a class/interface's type arguments
based on a subtype. It is far more limited in determining the type
arguments for the subject class's type variables in that it can only
determine those parameters that map from the subject Class
object
to the supertype.
Example: TreeSet
sets its parameter as the
parameter for NavigableSet
, which in turn
sets the parameter of SortedSet
, which in turn sets the
parameter of Set
, which in turn sets the parameter of
Collection
, which in turn sets the parameter of
Iterable
. Since TreeSet
's parameter maps
(indirectly) to Iterable
's parameter, it will be able to determine
that based on the super type Iterable<? extends
Map<Integer, ? extends Collection<?>>>
, the parameter of TreeSet
is ? extends Map<Integer, ? extends Collection<?>>
.
c
- the class whose type parameters are to be determined, not
null
superType
- the super type from which c
's type arguments are
to be determined, not null
Map
of the type assignments that could be determined for
the type variables in each type in the inheritance hierarchy from
type
to c
inclusive.public static final ParameterizedType parameterize(Class<?> raw, Map<TypeVariable<?>,Type> typeArgMappings)
raw
- the raw class to create a parameterized type instance fortypeArgMappings
- the mapping used for parameterizationParameterizedType
Copyright © 2015–2022 SciJava. All rights reserved.