这几天又重新学习了一下反射,略有感悟(以下是学习笔记):
镜像:类被加载到内存以后,通过类镜像来表示,java.lang.Class
反射:在运行时,通过类镜像进行类操作(获取类信息、构建类对象、调用方法等),使用java.lang.reflect包下的API(Field、Method、Constructor)
反射使用场景:当类的信息在编译时无法确定,运行时才能确定下来时,必须使用反射进行相关操作
反射编程步骤:
1)获取类镜像:java.lang.Class.forName(...)
2)如需要,创建类实例对象:Class-->newInstance()
3)调用反射相关API:
java.lang.reflect.Field
java.lang.reflect.Constructor
java.lang.reflect.Method
以下是一个当你不知道客户所用数据库类型时,依靠反射来获取类镜像的过程:
//这是db.cfg文件,要从中获取类名与方法名 driver=com.wsy.refluction.OracleDriver method=load //以下是Java程序 package com.wsy.refluction; import java.io.FileInputStream; import java.lang.reflect.Method; import java.util.Properties; interface Driver{ public void load(String info , String name); } class OracleDriver implements Driver{ @Override public void load(String info , String name) { System.out.println("This is OracleDriver " + "info:" + info + " " + "name:" + name); } } class MySQLDriver implements Driver{ @Override public void load(String info , String name) { System.out.println("This is MySQLDriver"); } } class SQLServerDriver implements Driver{ @Override public void load(String info , String name) { System.out.println("This is SQLServerDriver"); } } public class Refluction { public static void main(String[] args) { Properties prop = new Properties(); try { prop.load(new FileInputStream("src/com/wsy/refluction/db.cfg")); String driverName = prop.getProperty("driver"); String methodName = prop.getProperty("method"); //结果:com.wsy.refluction.OracleDriver System.out.println(driverName); Class<?> c = Class.forName(driverName); Object o = c.newInstance(); //结果:com.wsy.refluction.OracleDriver@15db9742 System.out.println(o); Method[] methods = c.getMethods(); for(Method method : methods) { if(method.getName().equals(methodName)) { //结果:This is OracleDriver //调用成员方法 method.invoke(o , new Object[] {"driver" , c.getName()}); //调用静态方法 //method.invoke(null , new Object[] {"driver" , c.getName()}); } } } catch (Exception e) { e.printStackTrace(); } } }
下面这个程序是通过反射来获取一个类的各种信息:
//随意定义一个类(这里以Student类为例) package com.wsy.refluction; public class Student implements Comparable<Object>{ private String name; private int age; public Student(){} public Student(String name,int age){ this.name = name; this.age = age; } public String getName(){ return name; } //public void setName(String name){ private void setName(String name){ this.name = name; } public int getAge(){ return age; } public void setAge(){ this.age = age; } public String toString(){ StringBuffer sb = new StringBuffer(); sb.append("name:"); sb.append(name); sb.append(",age:"); sb.append(age); return sb.toString(); } public boolean equals(Object o){ if(!(o instanceof Student)) return false; Student s = (Student)o; return ((s.name.equals(name)) && (s.age == age)); } public int hashCode(){ return name.hashCode() + age; } public int compareTo(Object o){ Student s = (Student)o; return s.age - age; } public static void talk(){ System.out.println("in Student talk()"); } } //以下是主程序 package com.wsy.refluction; import java.lang.reflect.*; public class ReflectionTest2{ public static void printClass(Class clazz){ Package pac = clazz.getPackage(); String pacName = pac.getName(); System.out.println("package " + pacName + ";"); int modify = clazz.getModifiers(); String modifier = Modifier.toString(modify); String className = clazz.getName(); boolean isInterface = clazz.isInterface(); String classFlag = ""; if(isInterface) classFlag = "interface"; else classFlag = "class"; System.out.println(modifier + " " + classFlag + " " + className + "{"); } public static void printField(Class clazz){ Field[] fields = clazz.getDeclaredFields(); String modifier; String type; String fieldName; for(int i = 0;i < fields.length;i++){ modifier = Modifier.toString(fields[i].getModifiers()); type = fields[i].getType().getName(); fieldName = fields[i].getName(); System.out.println(" " + modifier + " " + type + " " + fieldName + ";"); } } public static void printConstructor(Class clazz){ Constructor[] cons = clazz.getDeclaredConstructors(); String consInfo; for(int i = 0;i < cons.length;i++){ consInfo = cons[i].toGenericString(); System.out.println(" " + consInfo + "{...}"); } } public static void printMethod(Class clazz){ Method[] methods = clazz.getDeclaredMethods(); String methodInfo; for(int i = 0;i < methods.length;i++){ methodInfo = methods[i].toGenericString(); System.out.println(" " + methodInfo + "{...}"); } System.out.println("}"); } public static void main(String[] args)throws Exception{ if(args.length != 1){ System.out.println("Please input argument!"); System.exit(1); } Class clazz1 = Class.forName(args[0]); ClassLoader loader = new ClassLoader(){}; Class clazz2 = loader.loadClass(args[0]); System.out.println("clazz1:" + clazz1); System.out.println("clazz2:" + clazz2); Student stu = new Student(); Class clazz3 = stu.getClass(); Class clazz4 = com.wsy.refluction.Student.class; System.out.println("clazz3:" + clazz3); System.out.println("clazz4:" + clazz4); System.out.println("*********************"); printClass(clazz1); printField(clazz1); printConstructor(clazz1); printMethod(clazz1); System.out.println("*********************"); Constructor[] cons = clazz1.getConstructors(); Constructor con = null;; for(int i = 0;i < cons.length;i++){ if(cons[i].getParameterTypes().length != 2) continue; con = cons[i]; } Student s = (Student)con.newInstance(new Object[]{"Jack",20}); System.out.println("studnet:" + s); Method[] methods = clazz1.getDeclaredMethods(); Method method = null; Method method2 = null; for(int i = 0;i < methods.length;i++){ if("setName".equals(methods[i].getName())){ method = methods[i]; } if("talk".equals(methods[i].getName())){ method2 = methods[i]; } } // 如果是静态方法,第一个参数传null,如果没有参数,第二个传null method.setAccessible(true); method.invoke(s, new Object[]{"Tom"}); System.out.println(s); method2.invoke(null,new Object[]{}); } } //以下是运行结果 clazz1:class com.wsy.refluction.Student clazz2:class com.wsy.refluction.Student clazz3:class com.wsy.refluction.Student clazz4:class com.wsy.refluction.Student ********************* package com.wsy.refluction; public class com.wsy.refluction.Student{ private java.lang.String name; private int age; public com.wsy.refluction.Student(){...} public com.wsy.refluction.Student(java.lang.String,int){...} public boolean com.wsy.refluction.Student.equals(java.lang.Object){...} public java.lang.String com.wsy.refluction.Student.toString(){...} public int com.wsy.refluction.Student.hashCode(){...} public int com.wsy.refluction.Student.compareTo(java.lang.Object){...} public java.lang.String com.wsy.refluction.Student.getName(){...} private void com.wsy.refluction.Student.setName(java.lang.String){...} public static void com.wsy.refluction.Student.talk(){...} public void com.wsy.refluction.Student.setAge(){...} public int com.wsy.refluction.Student.getAge(){...} } ********************* studnet:name:Jack,age:20 name:Tom,age:20 in Student talk()