美文网首页
Java中的Type类型

Java中的Type类型

作者: juconcurrent | 来源:发表于2020-05-12 14:10 被阅读0次

Type的定义

/**
 * Type is the common superinterface for all types in the Java
 * programming language. These include raw types, parameterized types,
 * array types, type variables and primitive types.
 *
 * @since 1.5
 */
public interface Type {}

翻译成中文,大致如下:

在Java编程语言中,Type是所有类型的父接口。包括:

  1. 原始类型(raw types),对应Class实现类
  2. 参数化类型(parameterized types),对应ParameterizedType接口
  3. 泛型数组类型(array types),对应GenericArrayType接口
  4. 类型变量(type variables),对应TypeVariable接口
  5. 基本类型(primitive types),对应Class实现类
  6. 通配符类型(wildcard types),对应WildcardType接口

一个简单的例子

public class Main {

    public static void main(String[] args) throws NoSuchMethodException, SecurityException {
        Method method = Main.class.getMethod("testType",
                List.class, List.class, List.class, List.class, List.class, Map.class);

        // 按照声明顺序返回`Type对象`的数组
        Type[] types = method.getGenericParameterTypes();

        for (int i = 0; i < types.length; i++) {
            // 最外层都是ParameterizedType
            ParameterizedType pType = (ParameterizedType) types[i];
            // 返回表示此类型【实际类型参数】的`Type对象`的数组
            Type[] actualTypes = pType.getActualTypeArguments();
            for (int j = 0; j < actualTypes.length; j++) {
                Type actualType = actualTypes[j];
                System.out.print("(" + i + ":" + j + ")  类型【" + actualType + "】");
                if (actualType instanceof Class) {
                    System.out.println(" -> 类型接口【" + actualType.getClass().getSimpleName() + "】");
                } else {
                    System.out.println(" -> 类型接口【" + actualType.getClass().getInterfaces()[0].getSimpleName() + "】");
                }
            }
        }
    }

    public <T> void testType(List<String> a1,
                             List<ArrayList<String>> a2,
                             List<T> a3,
                             List<? extends Number> a4,
                             List<ArrayList<String>[]> a5,
                             Map<String, Integer> a6) {
    }
}

执行以上代码,我们得到以下结果:

(0:0)  类型【class java.lang.String】 -> 类型接口【Class】
(1:0)  类型【java.util.ArrayList<java.lang.String>】 -> 类型接口【ParameterizedType】
(2:0)  类型【T】 -> 类型接口【TypeVariable】
(3:0)  类型【? extends java.lang.Number】 -> 类型接口【WildcardType】
(4:0)  类型【java.util.ArrayList<java.lang.String>[]】 -> 类型接口【GenericArrayType】
(5:0)  类型【class java.lang.String】 -> 类型接口【Class】
(5:1)  类型【class java.lang.Integer】 -> 类型接口【Class】

类型可能出现的场景

  1. 修饰类的继承(extends)或实现(implements)关系类型
  2. 修饰类的参数类型
  3. 修饰字段的类型
  4. 修饰方法的请求参数类型
  5. 修饰方法的返回参数类型

ParameterizedType

ParameterizedType,叫做参数化类型,也叫泛型,指的是带尖括号的修饰符类型。例如:List<T>Map<Integer, String>List<? extends Number>

方法 - Type[] getActualTypeArguments();

  1. 表示此类型实际类型参数的Type对象的数组。
  2. 也就是说,获得参数化类型中<>里面的类型参数的类型。
  3. 可能有多个类型参数,例如Map<K, V>

方法 - Type getRawType();

  1. 返回Type对象,表示声明此类型的类或接口。
  2. 简单来说就是:返回最外层<>前面那个类型,例如Map<K ,V>,针对K或V来说,返回的就是Map类型。

方法 - Type getOwnerType();

  1. 返回Type对象,表示此类型是其成员之一的类型。
  2. 如果当前类型为顶层类型,则返回null(通常情况是这样)。
  3. 例如:Map.Entry中的Entry返回的就是MapA.B.C中的C返回的就是A$B

例子

public class Main {

    public static void main(String[] args) throws Exception {
        Method method = Main.class.getMethod("calc", List.class);
        Type[] types = method.getGenericParameterTypes();
        ParameterizedType listType = (ParameterizedType) types[0];
        System.out.println("listType.getRawType() is Class: " + (listType.getRawType() instanceof Class));
        System.out.println("listType.getRawType() return: " + listType.getRawType().getTypeName());

        ParameterizedType abctType = (ParameterizedType) listType.getActualTypeArguments()[0];
        System.out.println("abctType.getOwnerType() is Class: " + (abctType.getOwnerType() instanceof Class));
        System.out.println("abctType.getOwnerType() return: " + abctType.getOwnerType());
    }

    public <T> void calc(List<A.B.C<T>> list) {
    }

    interface A<T> {
        interface B<T> {
            interface C<T> {
            }
        }
    }
}

返回结果如下:

listType.getRawType() is Class: true
listType.getRawType() return: java.util.List
abctType.getOwnerType() is Class: true
abctType.getOwnerType() return: interface com.junconcurrent.Main$A$B

TypeVariable

TypeVariable,叫做类型变量,泛指任意类。例如:参数化类型中的E、K、V、T等。

方法 - Type[] getBounds();

  1. 返回表示此类型变量上边界的Type对象的数组。
  2. 【注意】:如果未显式声明上边界,则上边界为Object
  3. 【主要】:在类型变量中,只能有上边界,不能有下边界。例如:V super Xxx,将编译报错。

方法 - D getGenericDeclaration();

返回表示声明此类型变量的泛型声明的GenericDeclaration对象。

方法 - String getName();

返回此类型变量的名称,因为它出现在源代码中。

方法 - AnnotatedType[] getAnnotatedBounds();

返回AnnotatedType对象的数组,这些对象表示使用类型来表示此TypeVariable表示的类型参数的上限。

例子

public class Main {

    public static void main(String[] args) throws Exception {
        Method method = Main.class.getMethod("calc", List.class);
        Type[] types = method.getGenericParameterTypes();
        ParameterizedType listType = (ParameterizedType) types[0];
        System.out.println("listType.getRawType() is Class: " + (listType.getRawType() instanceof Class));
        System.out.println("listType.getRawType() return: " + listType.getRawType().getTypeName());

        TypeVariable abctType = (TypeVariable) listType.getActualTypeArguments()[0];
        System.out.println("abctType.getName() return: " + abctType.getName());
        System.out.println("abctType.getBounds() return: " + Arrays.toString(abctType.getBounds()));
        System.out.println("abctType.getGenericDeclaration() return: " + abctType.getGenericDeclaration());
    }

    public <T extends String & Map> void calc(List<T> list) {
    }
}

返回结果如下:

listType.getRawType() is Class: true
listType.getRawType() return: java.util.List
abctType.getName() return: T
abctType.getBounds() return: [class java.lang.String, interface java.util.Map]
abctType.getGenericDeclaration() return: public void com.junconcurrent.Main.calc(java.util.List)

GenericArrayType

GenericArrayType,叫做泛型数组类型,其组件类型为参数化类型或类型变量。例如:List<T>[]T[]。其和一般数组类型不太一样。如果方括号去掉之后的类型是参数化类型或者类型变量,那么其就是GenericArrayType。否则为一般数组类型,例如:List[]String[],其类型为Class

方法 - Type getGenericComponentType();

返回表示此数组的组件类型的Type对象。此方法用于获取数组的组件类型。

获取泛型数组中元素的类型,要注意的是:无论从左向右有几个[]并列,这个方法仅仅脱去最右边的[],之后剩下的内容就作为这个方法的返回值。

WildcardType

WildcardType为通配符类型表达式。例如:?? super T? extends T? extends Number

方法 - Type[] getUpperBounds();

返回表示此类型变量上边界的Type对象的数组。

【注意】:如果不存在显式声明的上边界,则上边界为Object

方法 - Type[] getLowerBounds();

返回表示此类型变量下边界的Type对象的数组。

【注意】:如果不存在显式声明的下边界,则下边界为类型 null。在此情况下,将返回长度为零的数组。

Class

除了上述4种类型之外,通常的类型或者原始类型,都是Class类型。

相关文章

  • java int和byte转换

    int转byte 在java中,宽类型(wider integer type)转窄类型(narrower type...

  • [Effective Java] Item 30: Use en

    在Java 1.5中,有两个类型被加入:enum type和annotation type。 在Java docs...

  • Tip | JNI数据类型与指针嵌套

    JNI数据类型 Java Type Java数据类型 Native Type Native层的数据类型 Descr...

  • java知识总结之Type

    参考 Java中的Type Type是Java 编程语言中所有类型的公共高级接口(官方解释),也就是Java中所有...

  • Java中的Type类型

    Type的定义 翻译成中文,大致如下: 在Java编程语言中,Type是所有类型的父接口。包括:原始类型(raw ...

  • Java中的Type类型

    [TOC] 学习之中涉及到了,找了几片文章学习了以下,这里做个记录: ParameterizedType参数化类型...

  • java 自动装箱和拆箱

    java 自动装箱和拆箱 Java数据类型 在Java中,数据类型可以分为两大种,Primitive Type(基...

  • Hibernate映射类型篇

    一、 Java类型 -Hibernate映射关系文件中,配置属性和字段关系时,可以在type属性上指定Java类型...

  • Java 类型总结

    title: Java Type 总结date: 2022/06/24 16:44 Java 类型总结 Type及...

  • 3. JNI basic

    java 数据类型在java源代码中,每个变量都必须声明一种类型(type)。有两种类型:primitive ty...

网友评论

      本文标题:Java中的Type类型

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