概述、
java反射机制是在运行状态中,可以拿到一个类一个对象,然后拿到所有的类中所有属性和方法。
查看类信息
获取class对象:
1.使用Class类的forName(String clazzName)方法。参数为完整类名。
2.调用某个类的class属性。
3.调用某个对象的getClass()方法。
//第一种方式
Class myClass=Class.forName("com.xxx.TestClass");
//第二中方式
Class myClass=TestClass.class;
//第三种方式
TestClass test=new TestClass();
Class myClass=test.getClass();
获取class对象的属性、方法
加Declared修饰表示所有,未加表示public;私有属性需要设置取消访问检查,调用setAccessible(boolean)。
所有成员属性:getDeclaredFields()或者getFields(),返回结果Field[]
单个成员属性:getDeclaredField()或者getField(),返回Field
所有方法:getDeclaredMethods()或者getMethods(),返回Method[]
单个方法:getMethod(),返回Method
所有构造:getDeclaredConstructors()或者getConstructors(),返回Constructor
//获取class对象的所有属性 数组
Field[] allFields = myClass.getDeclaredFields();
//获取class对象的public属性 数组
Field[] publicFields = myClass.getFields();
//获取class指定属性 如:年龄
Field ageField = myClass.getDeclaredField("age");
//获取class指定的public属性
Field desField = myClass.getField("des");
2.获取对象的方法
//获取class对象的所有声明方法
Method[] methods = myClass.getDeclaredMethods();
//获取class对象的所有public方法
Method[] allMethods = myClass.getMethods();
//返回次Class对象对应类的、带指定形参列表的public方法(setInfo:方法名,String.class,int.class...形参列表)
Method method = myClass.getMethod("setInfo", String.class,int.class);
//返回次Class对象对应类的、带指定形参列表的方法
Method declaredMethod = myClass.getDeclaredMethod("setAge",int.class);
3.获取构造函数
//获取class对象的所有声明构造函数
Constructor<?>[] allConstructors = myClass.
;
//获取class对象public构造函数
Constructor<?>[] publicConstructors = myClass.getConstructors();
//获取指定声明构造函数
Constructor<?> constructor = myClass.getDeclaredConstructor(String.class);
//获取指定声明的public构造函数
Constructor publicConstructor = myClass.getConstructor(String.class);
操作对象
生成类的实例对象
1.,Class对象的newInstance()
2.Constructor对象的newInstance()方法
//第一种方式 Class对象调用newInstance()方法生成
Object obj = class1.newInstance();
//第二种方式 对象获得对应的Constructor对象,再通过该Constructor对象的newInstance()方法生成
Constructor<?> constructor = class1.getDeclaredConstructor(String.class);//获取指定声明构造函数
obj = constructor.newInstance("hello");
调用类的方法
1.Class对象的getMethods()方法
2.调用Method对象中的Object invoke(Object obj, Object… args)方法.第一个参数表示method对象
代理
分类
静态代理:代理类是在编译时就实现好的
动态代理:代理类是在运行时生成的。
目标对象(RealSubject )以及代理对象(Proxy)都实现了主题接口(Subject)。代理对象(Proxy)中拥有目标对象(RealSubject )的实例,在实现主题接口(Subject)的方法中调用目标对象的方法(实现主接口的方法)。
动态代理:
java.lang.reflect.Proxy: 这是生成代理类的主类,Proxy提供了用户创建动态代理类和代理对象的静态方法.
java.lang.reflect.InvocationHandler: 这里称他为”调用处理器”,它是一个接口。当调用动态代理类中的方法时,将会直接转接到执行自定义的InvocationHandler中的invoke()方法。
创建动态代理实例的两种方法:
1.利用constructor.newInstance(handler)
//创建一个InvocationHandler对象
InvocationHandler handler = new MyInvocationHandler(.args..);
//使用Proxy生成一个动态代理类
//第一个参数是类加载器对象(即哪个类加载器来加载这个代理类到 JVM 的方法区),第二个参数是接口(表明你这个代理类需要实现哪些接口),第三个参数是调用处理器类实例(指定代理类中具体要干什么)
Class proxyClass = Proxy.getProxyClass(RealSubject.class.getClassLoader(),RealSubject.class.getInterfaces(), handler);
//获取proxyClass类中一个带InvocationHandler参数的构造器,用于下一步创建代理实例
Constructor constructor = proxyClass.getConstructor(InvocationHandler.class);
//调用constructor的newInstance方法来创建动态实例
RealSubject real = (RealSubject)constructor.newInstance(handler);
2.使用Proxy.newProxyInstance()
//创建一个InvocationHandler对象
InvocationHandler handler = new MyInvocationHandler(.args..);
//使用Proxy直接生成一个动态代理对象
RealSubject real =Proxy.newProxyInstance(RealSubject.class.getClassLoader(),RealSubject.class.getInterfaces(), handler);