Java Type类

news/2025/2/21 6:39:48/

文章目录

  • Type简介
  • Type分类
    • 1. 原始类型(Class)
    • 2. 参数化类型(ParameterizedType)
    • 3. 类型变量(TypeVariable)
    • 4. 通配符类型(WildcardType)
    • 5. 泛型数组类型(GenericArrayType)


Type简介

Type是Java编程语言中所有类型的公共高级接口。它们包括原始类型、参数化类型、数组类型、类型变量和基本类型。

Type接口本身算是一个标记接口,不提供任何需要复写的方法。

Type分类

在这里插入图片描述

Type分类:

Type分类名称Type类型描述举例
原始类型ClassJava类、枚举、数组、注解、所有基本数据类型StringDateIntegerintboolean
参数化类型ParameterizedType参数化类型(泛型类型)List<String>Map<Integer,String>List<T>List<?>、List<? extends Number>List<? super Number>
类型变量TypeVariable泛型符号(不包括通配符)TKVE
通配符类型WildcardType通配符?? extends Number? super Number
泛型数组类型GenericArrayType泛型数组List<?>[]List<T>[]List<String>[]List<? extends Number>[]T[]

获取Type:

JDK的Class、Field、Method类提供了一些列的获取类型的相关方法。

可参考文章:Java中如何获取泛型类型信息

1. 原始类型(Class)

原始类型的Type实现类为Class。这个类型与泛型无关,其它4个类型都和泛型相关。

原始类型主要包括:Java类、枚举、数组、注解、所有基本数据类型。

示例:

public class TypeTest {private String string;private Integer integer;private long lon;private int[] intArr;public static void main(String[] args) throws Exception {System.out.println(TypeTest.class.getDeclaredField("string").getGenericType() instanceof Class ? "String:是原始类型" : "String:不是原始类型");System.out.println(TypeTest.class.getDeclaredField("integer").getGenericType() instanceof Class ? "Integer:是原始类型" : "Integer:不是原始类型");System.out.println(TypeTest.class.getDeclaredField("lon").getGenericType() instanceof Class ? "long:是原始类型" : "long:不是原始类型");System.out.println(TypeTest.class.getDeclaredField("intArr").getGenericType() instanceof Class ? "int[]:是原始类型" : "int[]:不是原始类型");}
}

输出:

String:是原始类型
Integer:是原始类型
long:是原始类型
int[]:是原始类型

2. 参数化类型(ParameterizedType)

参数化类型的Type实现类为ParameterizedType。

参数化类型也就是泛型类型。

源码:

public interface ParameterizedType extends Type {Type[] getActualTypeArguments();Type getRawType();Type getOwnerType();
}

方法:

  • getActualTypeArguments:获取实际类型参数的Type集合
  • getRawType:获取声明此类型的类或接口的Type
  • getOwnerType:如果声明此类型的类或接口为内部类,这返回的是该内部类的外部类的Type(也就是该内部类的拥有者)

示例:

public class TypeTest<T> {private Map<Integer,String> map;private List<String> list1;private List<T> list2;private List<?> list3;private List<? extends Number> list4;public static void main(String[] args) throws Exception {System.out.println(TypeTest.class.getDeclaredField("map").getGenericType() instanceof ParameterizedType ? "Map<Integer,String>:是参数化类型" : "Map<Integer,String>:不是参数化类型");System.out.println(TypeTest.class.getDeclaredField("list1").getGenericType() instanceof ParameterizedType ? "List<String>:是参数化类型" : "List<String>:不是参数化类型");System.out.println(TypeTest.class.getDeclaredField("list2").getGenericType() instanceof ParameterizedType ? "List<T>:是参数化类型" : "List<T>:不是参数化类型");System.out.println(TypeTest.class.getDeclaredField("list3").getGenericType() instanceof ParameterizedType ? "List<?>:是参数化类型" : "List<?>:不是参数化类型");System.out.println(TypeTest.class.getDeclaredField("list4").getGenericType() instanceof ParameterizedType ? "List<? extends Number>:是参数化类型" : "List<? extends Number>:不是参数化类型");System.out.println("-----------------------------------------------------------");ParameterizedType parameterizedType = (ParameterizedType) TypeTest.class.getDeclaredField("map").getGenericType();for (Type actualTypeArgument : parameterizedType.getActualTypeArguments()) {System.out.println("getActualTypeArguments 方法返回值有:" + actualTypeArgument.getTypeName());}System.out.println("getRawType 方法返回值:" + parameterizedType.getRawType().getTypeName());System.out.println("getOwnerType 方法返回值:" + (parameterizedType.getOwnerType() != null ? parameterizedType.getOwnerType().getTypeName() : "null"));}
}

输出:

Map<Integer,String>:是参数化类型
List<String>:是参数化类型
List<T>:是参数化类型
List<?>:是参数化类型
List<? extends Number>:是参数化类型
-----------------------------------------------------------
getActualTypeArguments 方法返回值有:java.lang.Integer
getActualTypeArguments 方法返回值有:java.lang.String
getRawType 方法返回值:java.util.Map
getOwnerType 方法返回值:null

3. 类型变量(TypeVariable)

类型变量的Type实现类为TypeVariable。

类型变量急速指的泛型符号(不包括通配符)。
源码:

public interface TypeVariable<D extends GenericDeclaration> extends Type, AnnotatedElement {Type[] getBounds();D getGenericDeclaration();String getName();AnnotatedType[] getAnnotatedBounds();
}

方法:

  • getBounds:类型变量对应的上边界。如果没有指定上限,返回Object,可以有多个
  • getGenericDeclaration:获取类型变量所在类的Type。
  • getName:获取类型变量在源码中定义的名称
  • getAnnotatedBounds:获取注解类型的上限数组

示例:

public class TypeTest<T> {private List<T> list2;private List<?> list3;private List<? extends Number> list4;public static void main(String[] args) throws Exception {System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list2").getGenericType()).getActualTypeArguments()[0] instanceof TypeVariable ? "T:是类型变量" : "T:不是类型变量");System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list3").getGenericType()).getActualTypeArguments()[0] instanceof TypeVariable ? "?:是类型变量" : "?:不是类型变量");System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list4").getGenericType()).getActualTypeArguments()[0] instanceof TypeVariable ? "? extends Number:是类型变量" : "? extends Number:不是类型变量");System.out.println("---------------------------------------------------------------");TypeVariable typeVariable = (TypeVariable)((ParameterizedType) TypeTest.class.getDeclaredField("list2").getGenericType()).getActualTypeArguments()[0];for (Type bound : typeVariable.getBounds()) {System.out.println("getBounds 方法返回值有:" + bound.getTypeName());}System.out.println("getGenericDeclaration 方法返回值:" + typeVariable.getGenericDeclaration());System.out.println("getName 方法返回值:" + typeVariable.getName());for (AnnotatedType annotatedType : typeVariable.getAnnotatedBounds()) {System.out.println("getAnnotatedBounds 方法返回值有:" + annotatedType.getType().getTypeName());}}
}

输出:

T:是类型变量
?:不是类型变量
? extends Number:不是类型变量
---------------------------------------------------------------
getBounds 方法返回值有:java.lang.Object
getGenericDeclaration 方法返回值:class com.joker.test.generic.TypeTest
getName 方法返回值:T
getAnnotatedBounds 方法返回值有:java.lang.Object

4. 通配符类型(WildcardType)

通配符类型的Type实现类为WildcardType。

源码:

public interface WildcardType extends Type {Type[] getUpperBounds();Type[] getLowerBounds();
}

方法:

  • getUpperBounds:泛型表达式的上边界(表达式中使用extends)
  • getLowerBounds:泛型表达式的下边界(表达式中使用super)

示例:

public class TypeTest<T> {private List<T> list2;private List<?> list3;private List<? extends Number> list4;private List<? super Number> list5;public static void main(String[] args) throws Exception {System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list2").getGenericType()).getActualTypeArguments()[0] instanceof WildcardType ? "T:是通配符类型" : "T:不是通配符类型");System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list3").getGenericType()).getActualTypeArguments()[0] instanceof WildcardType ? "?:是通配符类型" : "?:不是通配符类型");System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list4").getGenericType()).getActualTypeArguments()[0] instanceof WildcardType ? "? extends Number:是通配符类型" : "? extends Number:不是通配符类型");System.out.println(((ParameterizedType)TypeTest.class.getDeclaredField("list5").getGenericType()).getActualTypeArguments()[0] instanceof WildcardType ? "? super Number:是通配符类型" : "? super Number:不是通配符类型");System.out.println("-----------------------------------------------");WildcardType wildcardType1 = (WildcardType)((ParameterizedType) TypeTest.class.getDeclaredField("list4").getGenericType()).getActualTypeArguments()[0];System.out.println("List<? extends Number> 上边界:"+wildcardType1.getUpperBounds()[0].getTypeName());WildcardType wildcardType2 = (WildcardType)((ParameterizedType) TypeTest.class.getDeclaredField("list5").getGenericType()).getActualTypeArguments()[0];System.out.println("List<? super Number> 上边界:"+wildcardType2.getUpperBounds()[0].getTypeName());System.out.println("List<? super Number> 下边界:"+wildcardType2.getLowerBounds()[0].getTypeName());}
}

输出:

T:不是通配符类型
?:是通配符类型
? extends Number:是通配符类型
? super Number:是通配符类型
-----------------------------------------------
List<? extends Number> 上边界:java.lang.Number
List<? super Number> 上边界:java.lang.Object
List<? super Number> 下边界:java.lang.Number

5. 泛型数组类型(GenericArrayType)

泛型数组类型的Type实现类为GenericArrayType。

注意:普通类型的数组不属于泛型数组类型(如int[]、Long[]、String[])。

源码:

public interface GenericArrayType extends Type {Type getGenericComponentType();
}

方法:

  • getGenericComponentType:返回泛型数组中成员类型

示例:

public class TypeTest<T> {private String[] list;private List<String>[] list1;private List<T>[] list2;private List<?>[] list3;private List<? extends Number>[] list4;private T[] list5;public static void main(String[] args) throws Exception {System.out.println(TypeTest.class.getDeclaredField("list").getGenericType() instanceof GenericArrayType ? "String[]:是泛型数组类型" : "String[]:不是泛型数组类型");System.out.println(TypeTest.class.getDeclaredField("list1").getGenericType() instanceof GenericArrayType ? "List<String>[]:是泛型数组类型" : "List<String>[]:不是泛型数组类型");System.out.println(TypeTest.class.getDeclaredField("list2").getGenericType() instanceof GenericArrayType ? "List<T>[]:是泛型数组类型" : "List<T>[]:不是泛型数组类型");System.out.println(TypeTest.class.getDeclaredField("list3").getGenericType() instanceof GenericArrayType ? "List<?>[]:是泛型数组类型" : "List<?>[]:不是泛型数组类型");System.out.println(TypeTest.class.getDeclaredField("list4").getGenericType() instanceof GenericArrayType ? "List<? extends Number>[]:是泛型数组类型" : "List<? extends Number>[]:不是泛型数组类型");System.out.println(TypeTest.class.getDeclaredField("list5").getGenericType() instanceof GenericArrayType ? "T[]:是泛型数组类型" : "T[]:不是泛型数组类型");System.out.println("------------------------------------------------------");System.out.println("List<String>[] 数组成员类型:"+((GenericArrayType) TypeTest.class.getDeclaredField("list1").getGenericType()).getGenericComponentType().getTypeName());System.out.println("List<T>[] 数组成员类型:"+((GenericArrayType) TypeTest.class.getDeclaredField("list2").getGenericType()).getGenericComponentType().getTypeName());System.out.println("List<?>[] 数组成员类型:"+((GenericArrayType) TypeTest.class.getDeclaredField("list3").getGenericType()).getGenericComponentType().getTypeName());System.out.println("List<? extends Number>[] 数组成员类型:"+((GenericArrayType) TypeTest.class.getDeclaredField("list4").getGenericType()).getGenericComponentType().getTypeName());System.out.println("T[] 数组成员类型:"+((GenericArrayType) TypeTest.class.getDeclaredField("list5").getGenericType()).getGenericComponentType().getTypeName());}
}

输出:

String[]:不是泛型数组类型
List<String>[]:是泛型数组类型
List<T>[]:是泛型数组类型
List<?>[]:是泛型数组类型
List<? extends Number>[]:是泛型数组类型
T[]:是泛型数组类型
------------------------------------------------------
List<String>[] 数组成员类型:java.util.List<java.lang.String>
List<T>[] 数组成员类型:java.util.List<T>
List<?>[] 数组成员类型:java.util.List<?>
List<? extends Number>[] 数组成员类型:java.util.List<? extends java.lang.Number>
T[] 数组成员类型:T

http://www.ppmy.cn/news/26130.html

相关文章

实战一(下):如何利用基于充血模型的DDD开发一个虚拟钱包系统?

上一节课,我们做了一些理论知识的铺垫性讲解,讲到了两种开发模式,基于贫血模型的传统开发模式,以及基于充血模型的DDD开发模式。今天&#xff0c;我们正式进入实战环节&#xff0c;看如何分别用这两种开发模式&#xff0c;设计实现一个钱包系统。话不多说&#xff0c;让我们正式…

【Java】线程的死锁和释放锁

线程死锁是线程同步的时候可能出现的一种问题 文章目录1. 线程的死锁1.1 基本介绍1.2 应用案例2. 释放锁2.1 下面的操作会释放锁2.2 下面的操作不会释放锁1. 线程的死锁 1.1 基本介绍 多个线程都占用了对方的锁资源&#xff0c;但不肯相让&#xff0c;导致了死锁&#xff0c;…

Elasticsearch进行优化-使用索引拆分(Split)和索引收缩(shrink )

一、索引拆分和收缩的场景 在Elasticsearch集群部署的初期我们可能评估不到位&#xff0c;导致分配的主分片数量太少&#xff0c;单分片的数据量太大&#xff0c;导致搜索时性能下降&#xff0c;这时我们可以使用Elasticsearch提供的Split功能对当前的分片进行拆分&#xff0c…

分享112个HTML娱乐休闲模板,总有一款适合您

分享112个HTML娱乐休闲模板&#xff0c;总有一款适合您 112个HTML娱乐休闲模板下载链接&#xff1a;https://pan.baidu.com/s/15uBy1SVSckPPMM55fiudeQ?pwdkqfz 提取码&#xff1a;kqfz Python采集代码下载链接&#xff1a;采集代码.zip - 蓝奏云 Bootstrap视频网站模板 …

解决Edge浏览器主页被篡改问题,或许可以帮你彻底解决

问题描述&#xff1a; 之前从一个第三方网站下载了一个不知名软件&#xff0c;接着电脑就各种下载360全家桶之类的软件&#xff0c;后来问题解决了&#xff0c;但是还残留了一些问题&#xff0c;前几天发现edge浏览器的主页被改成了360导航&#xff0c;就是那个该死的hao123&a…

webpack当中的代码分割详解

A.代码分割方法一&#xff1a;将原来的单入口文件改为多入口文件 将不同的文件例如js代码文件分为入口文件和测试文件&#xff0c;这个时候打包出来的代码就会根据不同的文件单独打包成属于他们自己的文件 例如以下为单入口文件: entry: ./src/js/index.js 多入口文件:(在输出…

ElementUI`resetFields()`方法避坑

使用ElementUI中的resetFields()方法有哪些注意点 场景一 场景一&#xff1a;当编辑弹出框和新增弹出框共用时&#xff0c;编辑数据后关闭编辑弹出框时调用this.$refs.form.resetFields()无法清空弹出框 问题代码&#xff1a; // 点击新增按钮handleAdd() {this.dialogVi…

音频信号处理笔记(一)

相关课程&#xff1a;【音频信号处理及深度学习教程】 文章目录01 信号的时域分析1.1 分帧1.1.1 幅值包络1.1.2 均方根能量0 信号的叠加&#xff1a;https://teropa.info/harmonics-explorer/ 一个复杂信号分解成若干简单信号分量之和。不同个频率信号的叠加: 由于和差化积&a…