如何在java中将带有泛型的类型转换为类?

如何在java中将带有泛型的类型转换为类?,java,generics,reflection,types,spring-properties,Java,Generics,Reflection,Types,Spring Properties,我有一个方法 我想用泛型提取returnType,并将其转换为类,以便将此类信息传递到SpringPropertyResolver Type type = myMethod.getGenericReturnType(); Class<?> returnType = /* ??? */; environment.getProperty(key, returnType); Type Type=myMethod.getGenericReturnType(); 类返回类型=/*???*/;

我有一个方法

我想用泛型提取return
Type
,并将其转换为
,以便将此类信息传递到Spring
PropertyResolver

Type type = myMethod.getGenericReturnType();
Class<?> returnType = /* ??? */;
environment.getProperty(key, returnType);
Type Type=myMethod.getGenericReturnType();
类返回类型=/*???*/;
getProperty(key,returnType);

您可以使用变通方法将
方法.getGenericReturnType()
返回的
java.lang.reflect.Type
转换为泛型的
类。

字符串分析:

final String typeName = method.getGenericReturnType().getTypeName();
Pattern pattern = Pattern.compile("<(.*)>");
final Matcher matcher = pattern.matcher(typeName);
if (matcher.find()) {
    String className = matcher.group(1);
    Class<?> clazz = Class.forName(className);        
}

实际上,return
Type
实例必须是以下之一:
Class
(例如
String
)、
genericarrytype
(例如
String[]
T[]
List[]
)、
TypeVariable
(例如
T
)或
parametricedtype
(例如
列表
列表
)。此外
类型
也可以是
通配符类型
(例如
列表
中的
),但不能直接用作返回类型

下面的代码尝试基于5个类中的子接口的实例来解析给定的类。如果
类型
很少不会扩展5个类中的任何一个,在这种情况下,我们只是说我们不能继续使用
不支持的操作异常
。例如,您可以创建自己的合成
类型
扩展类但你为什么要这么做

public static Class<?> type2Class(Type type) {
    if (type instanceof Class) {
       return (Class<?>) type;
    } else if (type instanceof GenericArrayType) {
       // having to create an array instance to get the class is kinda nasty 
       // but apparently this is a current limitation of java-reflection concerning array classes.
       return Array.newInstance(type2Class(((GenericArrayType)type).getGenericComponentType()), 0).getClass(); // E.g. T[] -> T -> Object.class if <T> or Number.class if <T extends Number & Comparable>
    } else if (type instanceof ParameterizedType) {
       return type2Class(((ParameterizedType) type).getRawType()); // Eg. List<T> would return List.class
    } else if (type instanceof TypeVariable) {
       Type[] bounds = ((TypeVariable<?>) type).getBounds();
       return bounds.length == 0 ? Object.class : type2Class(bounds[0]); // erasure is to the left-most bound.
    } else if (type instanceof WildcardType) {
       Type[] bounds = ((WildcardType) type).getUpperBounds();
       return bounds.length == 0 ? Object.class : type2Class(bounds[0]); // erasure is to the left-most upper bound.
    } else { 
       throw new UnsupportedOperationException("cannot handle type class: " + type.getClass());
    }
} 
公共静态类type2Class(类型){
if(类型instanceof Class){
返回(类)类型;
}else if(类型instanceof GenericArrayType){
//必须创建一个数组实例来获取类有点令人讨厌
//但显然,这是java反射在数组类方面的一个当前限制。
返回Array.newInstance(type2Class(((GenericaryType)type).getGenericComponentType()),0.getClass();//例如T[]->T->Object.class if或Number.class if
}else if(参数化类型的instanceof){
返回type2Class(((ParameterizedType)type).getRawType());//例如,List将返回List.class
}else if(类型instanceof TypeVariable){
类型[]边界=((TypeVariable)类型).getBounds();
return bounds.length==0?Object.class:type2Class(bounds[0]);//擦除位于最左边的边界。
}else if(类型instanceof WildcardType){
类型[]边界=((通配符类型)类型).getUpperBounds();
return bounds.length==0?Object.class:type2Class(bounds[0]);//擦除位于最左边的上限。
}否则{
抛出新的UnsupportedOperationException(“无法处理类型类:+type.getClass());
}
} 
请注意,代码未经测试,因此可能包含编译错误。此外,我不确定
GenericArrayType
如何处理多维数组类型,如
T[][]
(如果
,它可能会返回
Object[]
,而不是
Object[][]
,因此我们需要在这里做额外的工作).如果需要更正,请告诉我


最后,我们在这里要做的是计算给定
类型的擦除类
我想知道是否有一些“标准”代码就是这样做的,也许是Sun/Oracle编译器或代码分析器工具的一部分,您可以使用它们的实用程序,省去自己编写代码的麻烦并对其进行维护……我没有通过快速查看找到任何东西。

您看过这个吗?既然
getProperty
只接受
参数,为什么不直接使用
myMethod.getReturnType()
?@AndyTurner我将通过执行以下操作来释放泛型信息that@pixel但是由于
getProperty
只接受
Class
参数,而且没有
List.Class
这样的东西,例如,只接受
List.Class
,那么你还想怎么做呢?@你说得对-我需要做一些更复杂的事情为了用泛型转换值,我发现这段代码做了一些类似于我想要实现的事情:你打开类型参数而不是rawType有什么原因吗?这不是OP要求的吗?也许我理解错了。
public static Class<?> type2Class(Type type) {
    if (type instanceof Class) {
       return (Class<?>) type;
    } else if (type instanceof GenericArrayType) {
       // having to create an array instance to get the class is kinda nasty 
       // but apparently this is a current limitation of java-reflection concerning array classes.
       return Array.newInstance(type2Class(((GenericArrayType)type).getGenericComponentType()), 0).getClass(); // E.g. T[] -> T -> Object.class if <T> or Number.class if <T extends Number & Comparable>
    } else if (type instanceof ParameterizedType) {
       return type2Class(((ParameterizedType) type).getRawType()); // Eg. List<T> would return List.class
    } else if (type instanceof TypeVariable) {
       Type[] bounds = ((TypeVariable<?>) type).getBounds();
       return bounds.length == 0 ? Object.class : type2Class(bounds[0]); // erasure is to the left-most bound.
    } else if (type instanceof WildcardType) {
       Type[] bounds = ((WildcardType) type).getUpperBounds();
       return bounds.length == 0 ? Object.class : type2Class(bounds[0]); // erasure is to the left-most upper bound.
    } else { 
       throw new UnsupportedOperationException("cannot handle type class: " + type.getClass());
    }
}