MST

星途 面试题库

面试题:Java自定义泛型类与反射机制的深度结合

编写一个Java自定义泛型类`ReflectionGenericClass<T>`,在类中通过反射机制获取泛型参数`T`的构造函数,并使用反射创建`T`类型的实例。同时,要处理泛型类型擦除可能导致的问题,比如如何在运行时准确获取泛型实际类型信息。请详细阐述代码实现思路及每一步的作用。
43.5万 热度难度
编程语言Java

知识考点

AI 面试

面试题答案

一键面试

代码实现思路

  1. 定义泛型类ReflectionGenericClass:使用泛型参数T定义类,这样可以让类在实例化时指定具体的类型。
  2. 获取泛型实际类型信息:由于Java的泛型类型擦除,运行时无法直接获取泛型参数T的实际类型。因此,需要在构造函数中传入一个Class<T>类型的参数,通过这个参数来获取实际的类型信息。
  3. 获取构造函数并创建实例:使用传入的Class<T>对象获取T类型的构造函数,并通过构造函数创建T类型的实例。

代码实现

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;

public class ReflectionGenericClass<T> {
    private Class<T> clazz;

    // 构造函数,传入泛型类型的Class对象
    public ReflectionGenericClass(Class<T> clazz) {
        this.clazz = clazz;
    }

    // 创建泛型类型实例的方法
    public T createInstance() {
        try {
            // 获取无参构造函数
            Constructor<T> constructor = clazz.getConstructor();
            // 使用构造函数创建实例
            return constructor.newInstance();
        } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) {
            throw new RuntimeException("Failed to create instance", e);
        }
    }
}

代码解释

  1. 定义成员变量clazz:用于存储传入的泛型类型的Class对象。
  2. 构造函数ReflectionGenericClass(Class<T> clazz):接收一个Class<T>类型的参数,将其赋值给clazz成员变量,以便后续使用。
  3. createInstance方法
    • 获取无参构造函数:使用clazz.getConstructor()获取T类型的无参构造函数。如果T类型没有无参构造函数,会抛出NoSuchMethodException
    • 创建实例:通过调用构造函数的newInstance()方法创建T类型的实例。如果实例化过程中出现问题,如类是抽象类、接口或构造函数访问权限不足等,会抛出相应的异常,如InstantiationExceptionIllegalAccessException等。在捕获到异常后,通过throw new RuntimeException("Failed to create instance", e);将异常包装并抛出,方便上层调用者处理。

使用示例

public class Main {
    public static void main(String[] args) {
        // 创建ReflectionGenericClass实例,指定泛型类型为String
        ReflectionGenericClass<String> stringGenericClass = new ReflectionGenericClass<>(String.class);
        // 创建String实例
        String result = stringGenericClass.createInstance();
        System.out.println(result);
    }
}

在上述示例中,创建了ReflectionGenericClass<String>的实例,并调用createInstance方法创建了String类型的实例。这里使用String作为泛型类型,实际使用时可以替换为任何具有无参构造函数的类。