前情提要
本文章用于运行时获取泛型的具体类型,有一些情况下可以获取到真实类型,有一些情况下获取不到的情况。
Class 类的两个方法
/**
* Returns the {@code Class} representing the superclass of the entity
* (class, interface, primitive type or void) represented by this
* {@code Class}. If this {@code Class} represents either the
* {@code Object} class, an interface, a primitive type, or void, then
* null is returned. If this object represents an array class then the
* {@code Class} object representing the {@code Object} class is
* returned.
*
* @return the superclass of the class represented by this object.
* 用于获取this指代的对象的父类的类型,如果this指代的对象类型是Object,接口,基本类型,或void,方法返回null
* 如果this指代的是一个数组,则返回Object类型
* 这个方法会做泛型擦除,我们获取不到真实声明的泛型,我们要用下面的那个方法
*/
public native Class<? super T> getSuperclass();
/**
* Returns the {@code Type} representing the direct superclass of
* the entity (class, interface, primitive type or void) represented by
* this {@code Class}.
*
* <p>If the superclass is a parameterized type, the {@code Type}
* object returned must accurately reflect the actual type
* parameters used in the source code. The parameterized type
* representing the superclass is created if it had not been
* created before. See the declaration of {@link
* java.lang.reflect.ParameterizedType ParameterizedType} for the
* semantics of the creation process for parameterized types. If
* this {@code Class} represents either the {@code Object}
* class, an interface, a primitive type, or void, then null is
* returned. If this object represents an array class then the
* {@code Class} object representing the {@code Object} class is
* returned.
*
* @throws java.lang.reflect.GenericSignatureFormatError if the generic
* class signature does not conform to the format specified in
* <cite>The Java™ Virtual Machine Specification</cite>
* @throws TypeNotPresentException if the generic superclass
* refers to a non-existent type declaration
* @throws java.lang.reflect.MalformedParameterizedTypeException if the
* generic superclass refers to a parameterized type that cannot be
* instantiated for any reason
* @return the superclass of the class represented by this object
* @since 1.5
* 获取this对象的源代码中声明的父类类型,包括声明的泛型,即泛型未被擦除
* 我们的测试需要使用这个方法
*/
public Type getGenericSuperclass() {
ClassRepository info = getGenericInfo();
if (info == null) {
return getSuperclass();
}
// Historical irregularity:
// Generic signature marks interfaces with superclass = Object
// but this API returns null for interfaces
if (isInterface()) {
return null;
}
return info.getSuperclass();
}
测试代码
public class Main {
public static void main(String[] args) {
// TODO: 普通类继承抽象类 1=10
//带body实现和泛型指定
Type list1 = new ArrayList<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body
Type list2 = new ArrayList<String>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type list3 = new ArrayList<>() {
//}.getClass().getGenericSuperclass();
//什么都不带
Type list4 = new ArrayList<>().getClass().getGenericSuperclass();
// TODO: 接口 2=3
//带body实现和泛型指定
Type a1 = new Aoo<Double>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 编译报错 'Aoo' is abstract; cannot be instantiated
//Type a2 = new Aoo<Double>().getClass().getGenericSuperclass();
//带body不带泛型 编译报错 Cannot use "<>"with anonymous inner classes
//Type a3 = new Aoo<>() {
//}.getClass().getGenericSuperclass();
// TODO: 接口继承接口 3=2
//带body实现和泛型指定
Type c1 = new Coo<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 编译报错 'Coo' is abstract; cannot be instantiated
//Type c2 = new Coo<Double>().getClass().getGenericSuperclass();
//带body不带泛型 编译报错 Cannot use "<>"with anonymous inner classes
//Type c3 = new Coo<>() {
//}.getClass().getGenericSuperclass();
// TODO: 普通类实现接口 4=9
//带body实现和泛型指定
Type b1 = new Boo<Double>() {
}.getClass().getGenericSuperclass();
//带泛型不带body
Type b2 = new Boo<String>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type b3 = new Boo<>(){}.getClass().getGenericSuperclass();
//什么都不带
Type b4 = new Boo<>().getClass().getGenericSuperclass();
// TODO: 抽象类 5=6=7=8
//带body实现和泛型指定
Type foo1 = new Foo<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 编译报错 'Foo' is abstract; cannot be instantiated
//Type foo2=new Foo<String>().getClass().getGenericSuperclass();
//带body不带泛型 编译报错 Cannot use "<>"with anonymous inner classes
//Type foo3=new Foo<>(){}.getClass().getGenericSuperclass();
//TODO: 抽象类继承普通类 6=5=7=8
//带body实现和泛型指定
Type t1 = new Too<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 'Too' is abstract; cannot be instantiated
//Type t2 = new Too<String>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type t3 = new Too<>() {
//}.getClass().getGenericSuperclass();
// TODO: 抽象类继承抽象类 7=5=6=8
//带body实现和泛型指定
Type rpc1 = new QueueRpcSupport<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 编译报错 'QueueRpcSupport' is abstract; cannot be instantiated
//Type rpc2 = new QueueRpcSupport<String>().getClass().getGenericSuperclass();
//带body不带泛型 编译报错 Cannot use "<>"with anonymous inner classes
//Type rpc3 = new QueueRpcSupport<>() {
//}.getClass().getGenericSuperclass();
// TODO: 抽象类实现接口 8=5=6=7
//带body实现和泛型指定
Type d1 = new Doo<Double>() {
}.getClass().getGenericSuperclass();
//带泛型不带body 'Doo' is abstract; cannot be instantiated
//Type d2 = new Doo<String>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type d3 = new Doo<>(){}.getClass().getGenericSuperclass();
// TODO: 普通类 9=4
//带body实现和泛型指定
Type z1 = new Zoo<String>() {
}.getClass().getGenericSuperclass();
//带泛型不带body
Type z2 = new Zoo<String>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type z3 = new Zoo<>() {
//}.getClass().getGenericSuperclass();
//什么都不带
Type z4 = new Zoo<>().getClass().getGenericSuperclass();
// TODO: 2022/3/18 普通类继承普通类 10=1
//带body实现和泛型指定
Type x1 = new Xoo<String>() {
}.getClass().getGenericSuperclass();
//什么都不带
Type x2 = new Xoo<>().getClass().getGenericSuperclass();
//带body不带泛型,编译报错 Cannot use "<>"with anonymous inner classes
//Type x3 = new Xoo<>() {
//}.getClass().getGenericSuperclass();
//带泛型不带body
Type x4 = new Xoo<String>().getClass().getGenericSuperclass();
System.out.println("test");
}
}
//接口
interface Aoo<E> {
}
//接口继承接口
interface Coo<E> extends Aoo<E> {
}
//抽象类
abstract class Foo<T> {
}
//抽象类实现接口
abstract class Doo<E> implements Coo<E> {
}
//抽象类继承抽象类
abstract class QueueRpcSupport<T> extends Foo<T> {
}
//抽象类继承普通类
abstract class Too<E> extends Boo<E> {
}
//普通类
class Zoo<E> {
}
//普通类实现接口
class Boo<E> implements Aoo<E> {
}
//普通类继承普通类
class Xoo<E> extends Zoo<E> {
}
测试结果
结论
- 接口/普通类/抽象类的组合
接口 | 抽象类 | 普通类 | |
---|---|---|---|
接口 | 接口继承接口 | / | / |
抽象类 | 抽象类实现接口 | 抽象类继承抽象类 | 抽象类继承普通类 |
普通类 | 普通类实现接口 | 普通类继承抽象类 | 普通类继承普通类 |
- 结果分析