反射的操作方法

目标:通过反射获得User类的Class对象,得到该类的所有信息,构造User类的对象,调用普通方法,操作属性。

 *创建User类(方便演示)

package Reflect;

public class User {
	public int id;
	protected int age;
	private String uname;

	public User(){
		
	}
	public User(int id, int age, String uname) {
		super();
		this.id = id;
		this.age = age;
		this.uname = uname;
	}
	public int getId() {
		return id;
	}
	public void setId(int id) {
		this.id = id;
	}
	public int getAge() {
		return age;
	}
	public void setAge(int age) {
		this.age = age;
	}
	public String getUname() {
		return uname;
	}
	public void setUname(String uname) {
		this.uname = uname;
	}

}

(一) 获得该类的所有信息演示:

System.out.println("========================获得Class对象===================================");
Class class1=Class.forName("Reflect.User");
System.out.println("========================获得类的名字===================================");
System.out.println(class1.getName());//获得包名+类名
System.out.println(class1.getSimpleName());//获得类名
System.out.println("========================获得可访问属性===================================");
//获得public修饰的属性
Field[] field1=class1.getFields();
for(Field fs:field1){
	System.out.println(fs);
}
System.out.println("==========");
//获得所有的属性
Field[] field2=class1.getDeclaredFields();
for(Field fs:field2){
	System.out.println(fs);
}
System.out.println("==========");
//获得单独属性(name的属性)
Field field3=class1.getDeclaredField("name");
System.out.println(field3);
System.out.println("========================获得的类方法===================================");
//获取类的所有方法
Method[] methods=class1.getDeclaredMethods();
for(Method m:methods){
	System.out.println(m);
}
//获取类的单独方法
Method m01=class1.getDeclaredMethod("getUname", null);//用于区分重载方法
System.out.println(m01);
Method m02=class1.getDeclaredMethod("setUname", String.class);//用于区分重载方法
System.out.println(m02);

(二)构造User类对象


1)无参构造

方法一:
Class c=Class.forName("Reflect.User");
User u1=(User) c.newInstance();
方法二
Class<User> c=(Class<User>)Class.forName("Reflect.User");
User u1=c.newInstance();

2)有参构造

Constructor<User> c=clazz.getDeclaredConstructor(int.class,int.class,String.class);//获得有参构造器方法
User u2=c.newInstance(1,18,"wang2");
System.out.println(u2.getUname());//wang2

(三)调用普通方法

//方法一
User u3=clazz.newInstance();
u3.setUname("wang3");
//方法二(建议使用)
User u3=clazz.newInstance();
Method method=clazz.getDeclaredMethod("setUname",String.class);//获得了setUname(string){}方法
method.invoke(u3, "wang33"); //invoke表示激活
System.out.println(u3.getUname());

两方法比较:方法二更常用,因为获得的方法可以是从其他(数据库、游览器、文件)调过来的变量,体现反射的动态性,灵活度更高。

 

(四)操作属性

1)获得普通属性(注:用此方法获得私有属性会报错)

User u4=clazz.newInstance();
Field f=clazz.getDeclaredField("id");//获得了id属性
f.set(u4, 4);
System.out.println(u4.getId()); //4

2)获得private...等属性

User u4=clazz.newInstance();
Field f=clazz.getDeclaredField("uname");//获得uname属性
f.setAccessible(true);//这个属性不需要做安全检查,可以直接访问
f.set(u4, "wang4");
System.out.println(u4.getUname()); //System.out.println(f1.get(u4));

说明:setAccessible-启用和禁用访问安全检查的开关,true为关闭,false(默认)为开启。
注意:setAccessible检查需要耗时间,影响效率,有时候可以关闭以此来提高反射效率。

(五)操作泛型、操作注解(未完待续)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值