美文网首页
获取类或接口中的泛型

获取类或接口中的泛型

作者: 蜗蜗牛牛 | 来源:发表于2021-03-28 15:44 被阅读0次
    获取class的泛型.png 获取interface的泛型.png

    工具类

    public class GenericUtil {
    
        /**
         * 确定类在指定位置的泛型Class
         * 注意:匿名内部内要找到泛型,需要在实例化时在后面加{}
         *
         * @param clz            当前类
         * @param finalSupperClz 泛型最高父类
         * @param index          泛型在最高父类泛型中的位置
         * @param <T>
         * @return 泛型类
         * @throws IndexOutOfBoundsException
         * @throws ClassCastException
         * @throws IllegalArgumentException
         */
        public static <T> Class<T> getGenericClass(Class clz, Class finalSupperClz, int index) {
            return getGenericClass(clz, finalSupperClz.getName(), index);
        }
    
        public static <T> Class<T> getGenericClass(Class clz, String name, int index) {
            if (clz.getName().equals(name)) {
                //已经到需要的最顶级父类了,还是没找到泛型
                //不是泛型类,或者匿名内部内实现后面没带{}
                return null;
            }
            Type genericSuperclass = clz.getGenericSuperclass();
            if (!(genericSuperclass instanceof ParameterizedType)) {
                //当前类的父类没有泛型,去父类的父类中找
                return getGenericClass(clz.getSuperclass(), name, index);
            }
            ParameterizedType type = (ParameterizedType) genericSuperclass;
            String rawName = type.getRawType().getTypeName();
            if (!(rawName.equals(name))) {
                //父类名称不对,去父类的父类去找
                return getGenericClass(clz.getSuperclass(), name, index);
            }
    
            Type[] actualTypes = type.getActualTypeArguments();
            if (actualTypes.length <= index) {
                //泛型中,没有指定类型的泛型
                return null;
            }
    
            //由于泛型擦除,这里的强转即使类型不对也不会报错,但是在使用的时候就会报ClassCastException
            //所以在使用时看到这个错误,要去检查一下,对应index的泛型是不是写错了
            return (Class<T>) actualTypes[index];
        }
    
        /**
         * 确定接口实现类的指定位置泛型类
         */
        public static <T> Class<T> getGenericInterface(Class clz, Class interfaceClz, int index) {
            return getGenericInterface(clz, interfaceClz.getName(), index);
        }
    
        /**
         * 确定接口实现类的指定位置泛型类
         */
        public static <T> Class<T> getGenericInterface(Class clz, String name, int index) {
            if (clz.getName().equals(Object.class.getName())) {
                throw null;
            }
    
            Type[] genericInterfaces = clz.getGenericInterfaces();
            if (genericInterfaces.length <= index) {
                //当前类泛型数量小于index,去父类找
                return getGenericInterface(clz.getSuperclass(), name, index);
            }
    
            for (Type genericInterface : genericInterfaces) {
                if (genericInterface instanceof ParameterizedType) {
                    if (((ParameterizedType) genericInterface).getRawType().getTypeName().equals(name)) {
                        return (Class<T>) ((ParameterizedType) genericInterface).getActualTypeArguments()[0];
                    }
                }
            }
    
            return getGenericInterface(clz.getSuperclass(), name, index);
        }
    }
    

    相关文章

      网友评论

          本文标题:获取类或接口中的泛型

          本文链接:https://www.haomeiwen.com/subject/zqbphltx.html