反射机制
2016-04-25 10:52
603 查看
JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。
Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类;在运行时构造任意一个类的对象;在运行时判断任意一个类所具有的成员变量和方法;在运行时调用任意一个对象的方法;生成动态代理。
痛苦的反射机制,贴上代码和注释,一遍看代码一边学习
java的反射机制就是增加程序的灵活性,避免将程序写死到代码里
例如: 实例化一个 person()对象, 不使用反射, new person(); 如果想变成 实例化 其他类, 那么必须修改源代码,并重新编译。
使用反射: class.forName("person").newInstance(); 而且这个类描述可以写到配置文件中,如 **.xml, 这样如果想实例化其他类,只要修改配置文件的"类描述"就可以了,不需要重新修改代码并编译。
Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类;在运行时构造任意一个类的对象;在运行时判断任意一个类所具有的成员变量和方法;在运行时调用任意一个对象的方法;生成动态代理。
痛苦的反射机制,贴上代码和注释,一遍看代码一边学习
import java.lang.reflect.Array; import java.lang.reflect.Constructor; import java.lang.reflect.Field; import java.lang.reflect.Method; public class Reflection { /** * 得到某个对象的公共属性 * @param owner, fieldName * @return 该属性对象 * @throws Exception * */ public Object getProperty(Object owner, String fieldName) throws Exception { Class ownerClass = owner.getClass(); // 通过Object类的getClass()方法获取Class对象 Field field = ownerClass.getField(fieldName); // 返回Field对象 反映此Class对象所表示的类或接口的指定公共成员字段 Object property = field.get(owner); // 拿到对象实例的域成员的值 return property; } /** * 得到某类的静态公共属性 * @param className 类名 * @param fieldName 属性名 * @return 该属性对象 * @throws Exception */ public Object getStaticProperty(String className, String fieldName) throws Exception { Class ownerClass = Class.forName(className); //通过Class类的静态方法来获取Class对象 Field field = ownerClass.getField(fieldName); // Object property = field.get(ownerClass); return property; } /** * 执行某对象方法 * @param owner 对象 * @param methodName 方法名 * @param args 参数 * @return 方法返回值 * @throws Exception */ public Object invokeMethod(Object owner, String methodName, Object[] args) throws Exception { Class ownerClass = owner.getClass(); Class[] argsClass = new Class[args.length]; for (int i = 0, j = args.length; i < j; i++) { argsClass[i] = args[i].getClass(); } // 第一个参数是方法名,第二个参数是该方法的参数类型 // 因为存在同方法名不同参数这种情况,所以只有同时指定方法名和参数类型才能唯一确定一个方法 // 第一个参数是具体调用该方法的对象 第二个参数是执行该方法的具体参数 // 如一个函数 int Test(int a, String str); // 对应的getMethod方法: // 1. getMethod("Test",int.class,String.class); // 2. getMethod("Test",new Class[]{int.class,String.class}); Method method = ownerClass.getMethod(methodName, argsClass); // 然后通过invoke来调用此方法: // 函数原型:Object Java.lang.reflect.Method.invoke(Object receiver, Object... args) // Method类的invoke(Object obj,Object args[])方法接收的参数必须为对象, // 如果参数为基本类型数据,必须转换为相应的包装类型的对象。invoke()方法的返回值总是对象, // 如果实际被调用的方法的返回类型是基本类型数据,那么invoke()方法会把它转换为相应的包装类型的对象,再将其返回 // receiver:该方法所在类的一个对象 // args: 传入的参数 如 100,“hello” return method.invoke(owner, args); } /** * 执行某类的静态方法 * @param className 类名 * @param methodName 方法名 * @param args 参数数组 * @return 执行方法返回的结果 * @throws Exception */ public Object invokeStaticMethod(String className, String methodName, Object[] args) throws Exception { Class ownerClass = Class.forName(className); //通过Class类的静态方法来获取Class对象 Class[] argsClass = new Class[args.length]; for (int i = 0, j = args.length; i < j; i++) { argsClass[i] = args[i].getClass(); } Method method = ownerClass.getMethod(methodName, argsClass); return method.invoke(null, args); } /** * 新建实例 * * @param className * 类名 * @param args * 构造函数的参数 * @return 新建的实例 * @throws Exception */ public Object newInstance(String className, Object[] args) throws Exception { Class newoneClass = Class.forName(className); Class[] argsClass = new Class[args.length]; for (int i = 0, j = args.length; i < j; i++) { argsClass[i] = args[i].getClass(); } // 返回一个Constructor对象,它反映此Class对象所表示的类的指定公共构造。 // 参数是一个数组的Class对象识别的构造函数的形参类型,在声明的顺序。 // 例如: Constructor c = String.class.getConstructor( new Class[]{ String.class } ); Constructor cons = newoneClass.getConstructor(argsClass); // Class.newInstance() 只能够调用无参的构造函数,即默认的构造函数; 要求被调用的构造函数是可见的,也即必须是public类型的; // Constructor.newInstance() 可以根据传入的参数,调用任意构造构造函数;在特定的情况下,可以调用私有的构造函数。 return cons.newInstance(args); } /** * 是不是某个类的实例 * @param obj 实例 * @param cls 类 * @return 如果 obj 是此类的实例,则返回 true */ public boolean isInstance(Object obj, Class cls) { // 确定指定的对象是与这个类表示的对象赋值兼容的,如果是返回true return cls.isInstance(obj); } /** * 得到数组中的某个元素 * @param array 数组 * @param index 索引 * @return 返回指定数组对象中索引组件的值 */ public Object getByArray(Object array, int index) { return Array.get(array, index); } }
java的反射机制就是增加程序的灵活性,避免将程序写死到代码里
例如: 实例化一个 person()对象, 不使用反射, new person(); 如果想变成 实例化 其他类, 那么必须修改源代码,并重新编译。
使用反射: class.forName("person").newInstance(); 而且这个类描述可以写到配置文件中,如 **.xml, 这样如果想实例化其他类,只要修改配置文件的"类描述"就可以了,不需要重新修改代码并编译。
相关文章推荐
- java对世界各个时区(TimeZone)的通用转换处理方法(转载)
- java-注解annotation
- java-模拟tomcat服务器
- java-用HttpURLConnection发送Http请求.
- java-WEB中的监听器Lisener
- Android IPC进程间通讯机制
- Android Native 绘图方法
- Android java 与 javascript互访(相互调用)的方法例子
- 介绍一款信息管理系统的开源框架---jeecg
- 聚类算法之kmeans算法java版本
- java实现 PageRank算法
- PropertyChangeListener简单理解
- c++11 + SDL2 + ffmpeg +OpenAL + java = Android播放器
- 插入排序
- 冒泡排序
- 堆排序
- 快速排序
- 二叉查找树