【转】Java利用反射机制访问私有化构造器
我们都知道,当一个类的构造方法被设为私有的时候(private),在其他类中是无法用new来实例化一个对象的。
但是有一种方法可以把带有私有构造器的类实例化出对象。
在java的反射机制中,可以通过Class.forName(类名).newInstance()来实例化一个对象,还可以获取类的所有方法和构造方法。
Constructor这个类,表示类构造器,即构造方法。在生成类对象的时候,会调用构造方法。
- //例子程序
- import java.lang.reflect.Constructor;
- import java.lang.reflect.InvocationTargetException;
- import java.lang.reflect.Type;
- import java.util.ArrayList;
- import java.util.List;
- public class PrivateClassInstanceTest {
- static List<PrivateClassInstance> list = new ArrayList<PrivateClassInstance>();
- @SuppressWarnings("unchecked")
- public static void main(String[] args) {
- Constructor<PrivateClassInstance>[] constructors = null;
- try {
- // 拿到构造器数组,测试类包含多个私有构造器
- constructors = (Constructor<PrivateClassInstance>[]) Class.forName(
- "PrivateClassInstance").getDeclaredConstructors();
- } catch (ClassNotFoundException e) {
- e.printStackTrace();
- }
- // 按类中定义的顺序输出构造器
- for (int i = 0; i < constructors.length; i++) {
- Constructor<PrivateClassInstance> con = constructors[i];
- System.out.print(con + " ---> ");
- // 输出构造器参数的全部类型
- Type types[] = con.getGenericParameterTypes();
- int typeNums = types.length;
- for (int j = 0; j < typeNums; j++) {
- System.out.print(types[j]);
- }
- System.out.print(" ===> ");
- con.setAccessible(true); // 得到私有访问权限,如果不设置,则无法实例化对象
- //实例化对象
- PrivateClassInstance p;
- try {
- if (typeNums == 1) {
- p = con.newInstance(1);
- } else if (typeNums == 2) {
- p = con.newInstance("Li","nK");
- } else {
- p = con.newInstance();
- }
- list.add(p);
- } catch (IllegalArgumentException e) {
- e.printStackTrace();
- } catch (InstantiationException e) {
- e.printStackTrace();
- } catch (IllegalAccessException e) {
- e.printStackTrace();
- } catch (InvocationTargetException e) {
- e.printStackTrace();
- }
- }
- for(PrivateClassInstance p : list) {
- System.out.println(p);
- }
- }
- }
- class PrivateClassInstance {
- private PrivateClassInstance(String a, String b) {
- System.out.println("has two param");
- }
- private PrivateClassInstance() {
- System.out.println("no param");
- }
- private PrivateClassInstance(int n) {
- System.out.println("has one param");
- }
- }
输出结果:
private PrivateClassInstance(java.lang.String,java.lang.String) ---> class java.lang.Stringclass java.lang.String ===> has two param
private PrivateClassInstance() ---> ===> no param
private PrivateClassInstance(int) ---> int ===> has one param
PrivateClassInstance@c17164
PrivateClassInstance@1fb8ee3
PrivateClassInstance@61de33
最后打印出保存在list里的三个对象。
原文出处:http://wojiaorara.iteye.com/blog/1418359