Java的反射机制
为了在Java中对问题部分进行处理,我使用了反射API,并使用Class来获取类型信息。因为Class甚至可以处理原始类型,所以我经常使用Class,但现在我找到了反射的情况,所以只需要与以前的模式配合简单地进行备忘。
在使用反射时,有一些常见的类、字段、方法等选项,那么对于其他情况应该如何处理呢?
在传递参数的情况下是否用于判断的方法?
基本类型
在Java中,像int、long和double这样的基本数据类型并不是Class,但是它们都有对应的Class,在其中定义了Integer.TYPE等TYPE的常量。通过细致地比较这些类型信息,我们可以知道它们是哪一种类型。
可以通过获取类并使用Class#isPrimitive()方法来判断是原始类型还是对象。
数组
因为数组可以作为对象来处理,所以可以通过获取类 (Class) 来进行操作,并且可以通过 Class#isArray() 方法来进行检查。可以使用 Class#getComponentType() 等方法来获取元素的类型。
如果接收到的是一个数组,并且已经声明为Object类型,那么可以使用Array类来操作其元素。可以通过Arrays.asList((Object[])src)来将其转换为List类型,这是一种常见的写法。
当你掌握到这个程度,基本上你就能够进行类似对象映射的操作了。
泛型
使用List等<>来表示的表达,由于运行时的对象是使用new ArrayList<>()这样创建的,所以没有类型信息。在尝试将各种内容放入这样的定义中时,我遇到了转换的困难,但是看来Field似乎作为成员变量的类型信息是持有的,因此可以从那里获取。
class A<T> {
List<Integer> b = new ArrayList<T>();
}
由于无法获取类型为b的List,因此无法确定new ArrayList()的T等。这可能只对对象映射等方面有用,通常无需了解。
void example(Class<A> cls) {
String name = "b" // 変数名
// private から取得できる。 super classのものは cls.getSuperclass() などで別途取得しないと取れない
Field field = cls.getDeclaredField(name);
または
// public なものを継承関係も含めて取得できる
Field field = cls.getField(name);
Type type = field.getGenericType();
}
目前的新要素类型是一个称为Type的类型,其中包含了类型为cls的b的类型信息,并且它是Class的超类型。如果有泛型等附加元素,则会以Class以外的形式返回更多的信息。
如果使用了泛型,会返回有关 ParameterizedType 接口的信息。
ParameterizedType#getActualTypeArguments() 可以以一个数组的形式返回<>内的类型。这也是一个Type。如果类型是嵌套的,那么这里仍然是一个ParameterizedType,否则可以认为是一个Class。
使用ParameterizedType.getRawType()方法可以获取与传统的Class相同的Type。对于List
既然还可以使用List extends C>这样的表示法,那么在这种情况下会发生什么呢…