//如果成员变量是私有的,通过getDeclaredField(name)获取
Field field1 = clazz3.getField(“name”);
Field field2 = clazz3.getDeclaredField(“Id”);
//因为属性是私有的,获得属性之后,还有让其打开可见权限
field2.setAccessible(true);
//对其变量进行复制操作.
field1.setString(name,“小陈”);
field2.setInt(Id,150307);
//获取成员变量的值,通过field.get(obj) obj为所表示字段的对象
System.out.println(field2.get(person));
获取全员变量
Class clazz5 = Class.forName(“Rikka.Person”);
Person person = (Person)clazz5.newInstance();
person.setSex(“男”);
person.setName(“小郑”);
//获取所有私有属性
Field[] fields = clazz5.getDeclaredFields();
for(int i =0;i < fields.lenth;i++){
fields[i].setAccessible(true);
System.out.prinln(fields[i].get(person));
}
- 获得方法使用 Method
Class clazz6 = Class.forName(“Rikka.Person”);
Person person = (Person)clazz6.newInstance();
/**
如果为不带参数的方法,比如Person中的run()
**/
Method method1 = clazz6.getMethod(“run”);
/**
通过invole调用这个方法, invoke(obj,args)
obj为要使用方法的对象,args为参数列表,没有则不填
**/
method1.invoke(person);
//带参数的方法,比如Person中eat(String food)
Method method2 = clazz6.getMethod(“eat”,String.class);
method2.invoke(person,“三文鱼”);
//获得私有方法,比如Person中pay(int money)
Method method3 = clazz6.getDeclaredMethod(“pay”,int.class);
method3.setAccessible(true);
method3.invoke(person,443);
获取所有方法,同理啦。
Method[] methods = clazz6.getDeclaredMethods();
Person person = (Person)clazz6.newInstance;
for(Method method : methods){
method.setAccessible(true);
System.out.prinln(method.getName());
//获得方法参数,又回到了之前的代码
Class<?>[] parameterTypes = method.getParmeterTypes();
for(int j =0;j<parameterTypes.lenth;j++){
System.out.println(parameterTypes[j].getName()+",");
}
}
- 获取该类所有的接口
Class[] getInterfaces() :返回一个此对象所表示接口的类或者实现的接口的数组
- 获取指定资源的输入流
InputStream getResourceAsStream(Sting name)
return :一个InputStream对象
- 对于动态代理的影响
动态代理其实就是通过反射来生成一个代理。
在java.lang.reflect中提供了Proxy类和一个InvocationHandler接口,通过这个类和接口就可以生成动态代理对象。JDK中提供的代理只能针对接口代理。Proxy类中的方法创建动态代理对象分三步:
(1)new出代理对象:通过实现InvocationHandler接口,然后new出代理对象
(2)通过Proxy中的静态方法newProxyInstance,来将代理对象假装成那个被代理的对象(就跟替接了你的身份证帮你买车票一样)
(3)执行成功,代理成功。
下面为实现:
public class MyInvocationHandler implements InvocationHandler{
private Object target;
public MyInvocationHandler(Object target){
this.target = targetl
}
@Override
public Object invoke(Object proxy,Method method, Object[] args) throws Throwable{
System.out.println(“权限校验”);
method.invoke(target,args); //执行被代理target对象的方法
retrun null;
}
}
//想要代理方法的接口,比如说我是一个学生,我可以做login和submit两个动作
public interface Student{
public void login();
public void submit();
}
//本类,就是我这个学生,我login和submit时是怎么样做的。代理类代理的就是这个类。
public class StudentImp implments Student{
@Override
public void login(){
System.out.prinln(“login!”);
}
@Override
public void sumbit(){
System.out.prinln(“submit!”);
}
}
最后在我们要执行的地方
//new出一个被代理的类
Student simp = new StudentImp();
//我们要代理哪个真实对象,就将该对象传进去,最后是通过该真实对象来调用其方法的
MyInvocationHandler m = new MyInvocationHander(simp);
/*
-
通过Proxy的newProxyInstance方法来创建我们的代理对象,我们来看看其三个参数
-
第一个参数 m.getClass().getClassLoader() ,我们这里使用m这个类的ClassLoader对象来加载我们的代理对象
-
第二个参数simp.getClass().getInterfaces(),我们这里为代理对象提供的接口是真实对象所实行的接口,
-
表示我要代理的是该真实对象,这样我就能调用这组接口中的方法了
-
第三个参数m, 我们这里将这个代理对象关联到
了上方的MyInvocationHandler 这个对象上 -
第一个参数 m.getClass().getClassLoader() ,我们这里使用m这个类的ClassLoader对象来加载我们的代理对象
-
第二个参数simp.getClass().getInterfaces(),我们这里为代理对象提供的接口是真实对象所实行的接口,
-
表示我要代理的是该真实对象,这样我就能调用这组接口中的方法了
-
第三个参数m, 我们这里将这个代理对象关联到[外链图片转存中…(img-YSvkQjMg-1642923664399)]
了上方的MyInvocationHandler 这个对象上