不改变源代码的前提下,创建任意对象,执行任意方法

标题:不改变源代码的前提下,创建任意对象,执行任意方法

一、分析

  • public static void test(String path,String methodName,Class<?>[] parameterTypes,Object...params)
    path–>完整类名【包名.类名】
    methodName–>要执行的方法
    Class<?>[] parameterTypes–>方法中形参的class
    Object…params–>方法中形参对应的实参

  • Class<?> clazz = Class.forName(path);得到Class的类对象clazz

  • Object obj=clazz.getDeclaredConstructor().newInstance();//这就是反射为什么要无参构造器的原因,让每个类都有无参构造器比有参构造器更容易做到
    得到需要创建的对象【即Person】

  • Method method=clazz.getDeclaredMethod(methodName,parameterTypes);获得Class类对象clazz中的method对象【可以调用获得的类Person的方法】

  • method.setAccessible(true);便于访问私有方法

  • method.invoke(obj,params);调用方法

完整代码

/**
 * 小测试,不改变源代码的前提下,创建任意对象,执行任意方法,
 * 
 *  java.lang.NoSuchMethodException: crazyjava.reflect.Person.setName([Ljava.lang.Object;
 *  说明方法写错了,或者形参传错了
 * @author dell
 *
 */
public class TestDemo03 {
	public static void test(String path,String methodName,Class<?>[] parameterTypes,Object...params) throws Exception {
		Class<?> clazz = Class.forName(path);
		//创建对象
		Object obj=clazz.getDeclaredConstructor().newInstance();//这就是反射为什么要无参构造器的原因,让每个类都有无参构造器比有参构造器更容易做到
		
		
		 //获取Class<?>... parameterTypes
//		Class<?>[] parameterTypes=new Class<?>[params.length];//Class<?> 为什么要这样用-->任何类都可以用,为什么要加?,,,
//		for(int i=0;i<params.length;i++) {
//			parameterTypes[i]=params[i].getClass();
//		}
//		实际上parameterTypes都为Object.class,故仍旧是NoSuchMethodException
		
		//调用任何方法
		Method method=clazz.getDeclaredMethod(methodName,parameterTypes);//clazz.getMethod(String name, Class<?>... parameterTypes)
		method.setAccessible(true);
		method.invoke(obj,params);
		
//		method=clazz.getMethod("getName");
//		System.out.println(method.invoke(obj));
	}
	public static void main(String[] args) throws Exception {
		TestDemo03.test("crazyjava.reflect.Person","setName",new Class<?>[] {String.class},"jjj");
		TestDemo03.test("crazyjava.reflect.Person","setH",new Class<?>[] {String.class,String.class,int.class,double.class},"女","hhh",666,66.6);
	}
}

实体类的代码:

public class Person {
	private int id;
	public String name;
	public String sex;
	
	public int a;
	protected int b;
	int c;
	private int d;
	
	public Person() {
		
	}

	private Person(int id) {
		this.id=id;
	}
	
	private Person(String name) {
		this.name=name;
	}
	
	public int getId() {
		return id;
	}

	public void setId(int id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getA() {
		return a;
	}

	public void setA(int a) {
		this.a = a;
	}

	public int getB() {
		return b;
	}

	public void setB(int b) {
		this.b = b;
	}

	private int getC() {
		return c;
	}

	private void setC(int c) {
		this.c = c;
	}

	private int getD() {
		return d;
	}

	private void setD(int d) {
		this.d = d;
	}
	
	public void setSex(String sex) {
		this.sex=sex;
	}
	
	public String getSex() {
		return sex;
	}
	
	private void setH(String sex,String name,int id,double dou) {
		System.out.println(sex+"-->"+name+"-->"+id+"-->"+dou);
	}
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值