最近做了一个新的需求,要通过反射机制,获取A类中的私有子类a,并用该对象构建list<a>并塞入A的对象中。
主要思路是:(1)反射获取私有类;(2)构建私有类对象并反射插入list;(3)反射调用add方法。
查了挺多资料,但是很少有专门描述这个问题的。其难点主要在于编译时检测和参数无法匹配,通过多次反射才解决该问题,记录如下,直接上代码。
static void test2() { try { String str = "cn.com.template.data.transactiondata.orpo.TradedDetail"; Class<?> clazz = Class.forName(str); Object newInstance = clazz.newInstance(); for (Field field : clazz.getDeclaredFields()) { field.setAccessible(true); // System.out.println(field.getModifiers() + "\t" + field.getType() + "\t" + field.getName()); if (List.class.getName().equals(field.getType().getName())) { Type type = field.getGenericType(); if (type instanceof ParameterizedType) { ParameterizedType t = (ParameterizedType) type; String sublist = t.getActualTypeArguments()[0].getTypeName(); // System.out.println(">>>>>>>>>>>" + sublist); // 构建重复组,加载类 Class<?> list_clz = Class.forName(sublist); // System.out.println(list_clz.newInstance()); // 建立对象列表//创建对象list(List同样反射,越过泛型检查) List list = new ArrayList(); Method m = list.getClass().getMethod("add", Object.class); m.invoke(list, list_clz.newInstance()); // 调用set方法,塞入重复组 String methodName = "set" + field.getName().substring(0, 1).toUpperCase() + field.getName().substring(1); Method method = clazz.getMethod(methodName, List.class); method.invoke(newInstance, list); } } } // 打印结构体的json字符串 System.out.println(newInstance.toString()); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | NoSuchMethodException | SecurityException | IllegalArgumentException | InvocationTargetException e) { e.printStackTrace(); } }