Java反射08 : 成员方法Method学习示例
2018-03-04 14:36
513 查看
超级通道: Java泛型学习系列-绪论
java.lang.reflect.Method类提供了用于获取和操作成员方法的静态方法。
如何通过Class对象获取Method?如何通过Method对象获取Class?
如何通过Method获取成员方法的相关信息如:方法名、修饰符、参数个数、参数类型、参数化类型、异常类、可变参数、访问权限、注解?
如何通过构造器Method进行方法(包括私有方法)调用?
实例类:
Class对象与Method对象的相互转化
通过clazz.getMethod(name,args…)和clazz.getDeclaredMethod(name,args…)获取CLass对象的指定方法
通过clazz.getMethods()和clazz.getDeclaredMethods()获取CLass对象的全部方法
通过method.getDeclaringClass()获取当前Method对象所属的Class
Method信息获取
通过method.getModifiers()获取方法修饰符的int值
通过method.getName()获取方法名
通过method.getGenericReturnType()获取返回值的类型(Type),method.getReturnType()获取返回值的类(Class)
通过method.getGenericParameterTypes()获取参数的类型(Type),method.getParameterTypes()获取参数的类(Class)
通过method.getParameters()获取参数对象(Parameter[])数组
通过method.getGenericExceptionTypes()获取异常的类型(Type),method.getExceptionTypes()获取异常的类(Class)
通过method.toString()和method.toGenericString()获取方法的字符串描述
通过equals()比较两个方法是否相同
通过method.isBridge()判断是否是桥方法
通过method.isSynthetic()判断是否是合成方法
通过method.isVarArgs()判断是否使用了可变参数
通过method.getParameterCount()获取参数个数
通过method.getDefaultValue()获取默认返回值
通过method.getTypeParameters()获取泛型方法的参数化类型(泛型)
通过method.getAnnotatedXxxxType()获取被注解的类型(组合类型),Xxxx=[Return,Parameter,Exception,Receiver]
通过method.getAnnotation(Annotation.class)和method.getDeclaredAnnotation(Annotation.class)获取指定的注解
通过method.getAnnotationsByType(MyAnnotation.class)和method.getDeclaredAnnotationsByType(MyAnnotation.class)获取一组注解
通过method.getAnnotations()和method.getDeclaredAnnotations()获取全部注解
通过method.getParameterAnnotations()获取方法的所有参数注解(二维矩阵),数组元素表示第i个参数的第j个注解。
Method调用方法
通过method.invoke(user,args…)调用方法
可以通过method.setAccessible(true)将私有方法private method设置为可访问的,从而操作私有方法
备注:
有关获取Class对象的三种方式参见:Java反射02 : Class对象获取的三种方式和通过反射实例化对象的两种方式
有关getXxxx和getDeclaredXxxx参见:Java反射 : Declared的作用 ( 例如 : getMethods和getDeclaredMethods )
有关Class与Type参见: Java中Type接口与Class类的区别联系
有关参数化类型(泛型)参见系列:Java泛型学习系列-绪论
有关参数类(Parameter)参见后续章节:Java反射09 : 参数Parameter学习示例
使用成员方法Method进行反射编程的主要用法:通过成员方法Method进行方法(包括private)调用
java.lang.reflect.Method类提供了用于获取和操作成员方法的静态方法。
1.通过Method可以做什么
通过Method可以做以下事情:如何通过Class对象获取Method?如何通过Method对象获取Class?
如何通过Method获取成员方法的相关信息如:方法名、修饰符、参数个数、参数类型、参数化类型、异常类、可变参数、访问权限、注解?
如何通过构造器Method进行方法(包括私有方法)调用?
2.代码实例
实体类:/** * <p>用户表</p> * * @author hanchao 2018/2/14 22:30 */ public class User extends{ public String username = "张三"; private int password = 123456; //setter getter toString constructor ... /** * <p>Title: 为了测试可变参数</p> * * @author 韩超 2018/2/28 17:32 */ public void demo(String... args) { } /** * <p>Title: 泛型方法:为了测试method.getTypeParameters()参数化类型(泛型)</p> * * @author 韩超 2018/2/28 17:30 */ public static <T> void test(T t) { } /** * <p>为了测试通过Method获取参数注解的二维矩阵</p> * * @author hanchao 2018/3/4 14:24 **/ public void initUser(@MyAnnotationA @MyAnnotationB String username, @MyAnnotationB String password) { } /** * <p>私有方法,用来示例:通过反射调用私有方法</p> * * @author hanchao 2018/3/4 14:11 **/ private void setUsernameByDefault() { this.username = "default"; } /** * <p>Title: 为了测试注解、异常</p> * * @author 韩超 2018/2/28 17:31 */ @MyAnnotationA @MyAnnotationB public String getUsername() throws NullPointerException, ArrayStoreException { return username; } public void setUsername(String username) { this.username = username; } public int getPassword() { return password; } public void setPassword(int password) { this.password = password; } }
实例类:
/** * java.lang.reflect.Method示例 * Created by 韩超 on 2018/2/28. */ public class ReflectMethodDemo { private final static Logger LOGGER = Logger.getLogger(ReflectMethodDemo.class); /** * <p>Title: java反射-方法Method示例</p> * * @author 韩超 2018/2/28 14:54 */ public static void main(String[] args) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException { //首先获取Class对象 Class userClass = User.class; ////////////////////////////////////// Class对象与Method对象的相互转化 ///////////////////////////////////// LOGGER.info("////////////////////////////////////// Class对象与Method对象的相互转化 /////////////////////////////////////"); //通过clazz.getMethod(name,args...)和clazz.getDeclaredMethod(name,args...)获取CLass对象的指定方法 Method getUsrMethod = userClass.getMethod("getUsername"); Method setUsrMethod = userClass.getDeclaredMethod("setUsername", String.class); LOGGER.info("通过clazz.getMethod(name,args)获取CLass对象的指定方法:" + getUsrMethod); LOGGER.info("通过clazz.getDeclaredMethod(name,args)获取CLass对象的指定方法:" + setUsrMethod + "\n"); //通过clazz.getMethods()和clazz.getDeclaredMethods()获取CLass对象的全部方法 Method[] methods = userClass.getMethods(); for (Method method : methods) { LOGGER.info("通过clazz.getMethods()获取CLass对象的全部方法:" + method); } Method[] methods1 = userClass.getDeclaredMethods(); for (Method method : methods1) { LOGGER.info("通过clazz.getDeclaredMethods()获取CLass对象的全部方法:" + method); } System.out.println(); //通过method.getDeclaringClass()获取当前Method对象所属的Class Class userClass2 = getUsrMethod.getDeclaringClass(); LOGGER.info("通过method.getDeclaringClass()获取当前Method对象所属的Class:" + userClass2 + "\n"); ////////////////////////////////////// Method信息获取 ///////////////////////////////////// LOGGER.info("////////////////////////////////////// Method信息获取 /////////////////////////////////////"); //通过method.getModifiers()获取方法修饰符的int值 LOGGER.info("通过method.getModifiers()获取方法修饰符的int值" + Modifier.toString(getUsrMethod.getModifiers()) + "\n"); //通过method.getName()获取方法名 LOGGER.info("通过method.getName()获取方法名" + getUsrMethod.getName() + "\n"); //通过method.getGenericReturnType()获取返回值的类型(Type) LOGGER.info("通过method.getGenericReturnType()获取返回值的类型(Type):" + getUsrMethod.getGenericReturnType()); //通过method.getReturnType()获取返回值的类(Class) LOGGER.info("通过method.getReturnType()获取返回值的类(Class):" + getUsrMethod.getReturnType() + "\n"); //通过method.getGenericParameterTypes()获取参数的类型(Type) Type[] paramTypes = setUsrMethod.getGenericParameterTypes(); for (Type type : paramTypes) { LOGGER.info("通过method.getGenericParameterTypes()获取参数的类型(Type):" + type.getTypeName()); } //通过method.getParameterTypes()获取参数的类(Class) Class[] paramClasses = setUsrMethod.getParameterTypes(); for (Class clazz : paramClasses) { LOGGER.info("通过method.getParameterTypes()获取参数的类(Class):" + clazz); } System.out.println(""); //通过method.getParameters()获取参数(Parameter)数组 Parameter[] parameters = setUsrMethod.getParameters(); for (Parameter parameter : parameters) { LOGGER.info("通过method.getParameters()获取参数(Parameter)数组:" + parameter); } System.out.println(); //通过method.getGenericExceptionTypes()获取异常的类型(Type) Type[] exceptionTypes = getUsrMethod.getGenericExceptionTypes(); for (Type exception : exceptionTypes) { LOGGER.info("通过method.getGenericExceptionTypes()获取异常的类型(Type):" + exception.getTypeName()); } //通过method.getExceptionTypes()获取异常的类(Class) Class[] exceptionClasses = getUsrMethod.getExceptionTypes(); for (Class exception : exceptionClasses) { LOGGER.info("通过method.getExceptionTypes()获取异常的类(Class):" + exception); } System.out.println(); //通过method.toString()和method.toGenericString()获取方法的字符串描述 LOGGER.info("通过method.toString()获取方法的字符串描述:" + getUsrMethod.toString()); LOGGER.info("通过method.toGenericString()获取方法的字符串描述(包括通用类型):" + getUsrMethod.toGenericString() + "\n"); //通过equals()比较两个方法是否相同 LOGGER.info("通过equals()比较两个方法是否相同:" + getUsrMethod.equals(setUsrMethod)); //通过method.isBridge()判断是否是桥方法 LOGGER.info("通过method.isBridge()判断是否是桥方法:" + getUsrMethod.isBridge()); //通过method.isSynthetic()判断是否是合成方法 LOGGER.info("通过method.isSynthetic()判断是否是合成方法:" + getUsrMethod.isSynthetic()); //通过method.isVarArgs()判断是否使用了可变参数: Method demoMethod = userClass.getDeclaredMethod("demo", String[].class); LOGGER.info("通过method.isVarArgs()判断是否使用了可变参数:" + demoMethod.isVarArgs() + "\n"); //通过method.getParameterCount()获取参数个数 LOGGER.info("通过method.getParameterCount()获取参数个数,setUsername = " + setUsrMethod.getParameterCount()); LOGGER.info("通过method.getParameterCount()获取参数个数,getUsername = " + getUsrMethod.getParameterCount() + "\n"); //通过method.getDefaultValue()获取默认返回值 LOGGER.info("通过method.getDefaultValue()获取默认返回值,setUsername = " + setUsrMethod.getDefaultValue()); LOGGER.info("通过method.getDefaultValue()获取默认返回值,getUsrMethod = " + getUsrMethod.getDefaultValue() + "\n"); //通过method.getTypeParameters()获取泛型方法的参数化类型(泛型) TypeVariable[] typeVariables = getUsrMethod.getTypeParameters(); LOGGER.info("通过method.getTypeParameters()获取泛型方法的参数化类型(泛型),getUsrMethod()的参数化类型个数:" + typeVariables.length); Method toArrayMethod = userClass.getDeclaredMethod("test", Object.class); TypeVariable[] typeVariables1 = toArrayMethod.getTypeParameters(); LOGGER.info("通过method.getTypeParameters()获取泛型方法的参数化类型(泛型),ReflectMethodDemo.test()的参数化类型:" + typeVariables1[0].getName() + "\n"); ////////////////////////////////////// Method注解信息获取 ///////////////////////////////////// LOGGER.info("////////////////////////////////////// Method注解信息获取 /////////////////////////////////////"); //通过method.getAnnotatedReturnType()获取被注解的返回值类型(组合类型) AnnotatedType returnAnnotatedType = getUsrMethod.getAnnotatedReturnType(); LOGGER.info("通过method.getAnnotatedReturnType()获取被注解的返回值类型(组合类型):" + returnAnnotatedType); //获取被注解的返回值类型中的返回值类型 LOGGER.info("通过annotatedType.getType()获取被注解的返回值类型中的返回值类型:" + returnAnnotatedType.getType()); //获取被注解的返回值类型中的注解类型 Annotation[] annotations = returnAnnotatedType.getAnnotations(); LOGGER.info("通过annotatedType.getAnnotations()获取被注解的返回值类型中的注解类型"); setUsrMethod.getAnnotatedParameterTypes(); setUsrMethod.getAnnotatedExceptionTypes(); setUsrMethod.getAnnotatedReceiverType(); LOGGER.info("类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedParameterTypes()"); LOGGER.info("类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedExceptionTypes()"); LOGGER.info("类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedReceiverType()" + "\n"); //获取指定的单个注解 Annotation annotation = getUsrMethod.getAnnotation(MyAnnotationA.class); Annotation annotation1 = getUsrMethod.getDeclaredAnnotation(MyAnnotationB.class); LOGGER.info("通过method.getAnnotation(Annotation.class)获取指定的注解: " + annotation); LOGGER.info("通过method.getDeclaredAnnotation(Annotation.class)获取指定的注解 :" + annotation1 + "\n"); //获取指定的一类注解 Annotation[] annotations1 = getUsrMethod.getAnnotationsByType(MyAnnotationA.class); for (Annotation annotation11 : annotations1) { LOGGER.info("通过method.getAnnotationsByType(MyAnnotation.class)获取一类注解: " + annotation11); } Annotation[] annotations2 = getUsrMethod.getDeclaredAnnotationsByType(MyAnnotationA.class); for (Annotation annotation22 : annotations2) { LOGGER.info("通过method.getDeclaredAnnotationsByType(MyAnnotation.class)获取一类注解: " + annotation22); } System.out.println(""); //获取全部的注解 Annotation[] annotations3 = getUsrMethod.getAnnotations(); for (Annotation annotation33 : annotations3) { LOGGER.info("通过method.getAnnotations()获取全部注解: " + annotation33); } Annotation[] annotations4 = getUsrMethod.getDeclaredAnnotations(); for (Annotation annotation44 : annotations4) { LOGGER.info("通过method.getDeclaredAnnotations()获取全部注解: " + annotation44); } System.out.println(""); //获取注解参数的方法 Method initUserMethod = userClass.getDeclaredMethod("initUser", String.class, String.class); //通过method.getParameterAnnotations()获取方法的所有参数注解(二维矩阵) LOGGER.info("通过method.getParameterAnnotations()获取方法的所有参数注解(二维矩阵)"); Annotation[][] annotations5 = initUserMethod.getParameterAnnotations(); for (int i = 0; i < annotations5.length; i++) { //第一个维度标识的是第i个参数的所有注解 Annotation[] paramAnnotations = annotations5[i]; for (int j = 0; j < paramAnnotations.length; j++) { //第二个维度标识的是第i个参数的第j个注解 Annotation paramAnnotation = paramAnnotations[j]; LOGGER.info("第" + (i + 1) + "个参数,第" + (j + 1) + "个注解: " + paramAnnotation); } } System.out.println(""); LOGGER.info("////////////////////////////// Method 调用方法 ///////////////////////////////"); ////////////////////////////// Method 调用方法 /////////////////////////////// User user = new User(); LOGGER.info("通过直接方法user.getUsername()获取 user.username = " + user.getUsername()); //通过method.invoke(user,args...)调用方法 LOGGER.info("通过反射方法method.invoke(user,args...)设置 user.username"); setUsrMethod.invoke(user, "张三丰"); LOGGER.info("通过反射方法method.invoke(user,args...)获取 user.username = " + getUsrMethod.invoke(user) + "\n"); //可以通过method.setAccessible(true)将私有方法private method设置为可访问的,从而操作私有方法 Method privateMethod = userClass.getDeclaredMethod("setUsernameByDefault"); LOGGER.info("私有成员变量:" + privateMethod); LOGGER.info("可以通过method.setAccessible(true)将私有方法private method设置为可访问的,从而操作私有方法"); privateMethod.setAccessible(true); LOGGER.info("操作私有成员方法" ); privateMethod.invoke(user); LOGGER.info("查看私有成员方法调用结果:" + user.toString()); } }
3.运行结果
2018-03-04 14:18:49 INFO ReflectMethodDemo:28 - ////////////////////////////////////// Class对象与Method对象的相互转化 ///////////////////////////////////// 2018-03-04 14:18:49 INFO ReflectMethodDemo:32 - 通过clazz.getMethod(name,args)获取CLass对象的指定方法:public java.lang.String pers.hanchao.reflect.common.User.getUsername() throws java.lang.NullPointerException,java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:33 - 通过clazz.getDeclaredMethod(name,args)获取CLass对象的指定方法:public void pers.hanchao.reflect.common.User.setUsername(java.lang.String) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public java.lang.String pers.hanchao.reflect.common.User.toString() 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public static void pers.hanchao.reflect.common.User.test(java.lang.Object) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public java.lang.String pers.hanchao.reflect.common.User.getUsername() throws java.lang.NullPointerException,java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.setUsername(java.lang.String) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.demo(java.lang.String[]) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.initUser(java.lang.String,java.lang.String) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public int pers.hanchao.reflect.common.User.getPassword() 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.setPassword(int) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final void java.lang.Object.wait() throws java.lang.InterruptedException 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final void java.lang.Object.wait(long,int) throws java.lang.InterruptedException 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final native void java.lang.Object.wait(long) throws java.lang.InterruptedException 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public boolean java.lang.Object.equals(java.lang.Object) 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public native int java.lang.Object.hashCode() 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final native java.lang.Class java.lang.Object.getClass() 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final native void java.lang.Object.notify() 2018-03-04 14:18:49 INFO ReflectMethodDemo:38 - 通过clazz.getMethods()获取CLass对象的全部方法:public final native void java.lang.Object.notifyAll() 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public java.lang.String pers.hanchao.reflect.common.User.toString() 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public static void pers.hanchao.reflect.common.User.test(java.lang.Object) 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public java.lang.String pers.hanchao.reflect.common.User.getUsername() throws java.lang.NullPointerException,java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.setUsername(java.lang.String) 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.demo(java.lang.String[]) 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.initUser(java.lang.String,java.lang.String) 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:private void pers.hanchao.reflect.common.User.setUsernameByDefault() 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public int pers.hanchao.reflect.common.User.getPassword() 2018-03-04 14:18:49 INFO ReflectMethodDemo:42 - 通过clazz.getDeclaredMethods()获取CLass对象的全部方法:public void pers.hanchao.reflect.common.User.setPassword(int) 2018-03-04 14:18:49 INFO ReflectMethodDemo:48 - 通过method.getDeclaringClass()获取当前Method对象所属的Class:class pers.hanchao.reflect.common.User 2018-03-04 14:18:49 INFO ReflectMethodDemo:51 - ////////////////////////////////////// Method信息获取 ///////////////////////////////////// 2018-03-04 14:18:49 INFO ReflectMethodDemo:53 - 通过method.getModifiers()获取方法修饰符的int值public 2018-03-04 14:18:49 INFO ReflectMethodDemo:56 - 通过method.getName()获取方法名getUsername 2018-03-04 14:18:49 INFO ReflectMethodDemo:59 - 通过method.getGenericReturnType()获取返回值的类型(Type):class java.lang.String 2018-03-04 14:18:49 INFO ReflectMethodDemo:61 - 通过method.getReturnType()获取返回值的类(Class):class java.lang.String 2018-03-04 14:18:49 INFO ReflectMethodDemo:66 - 通过method.getGenericParameterTypes()获取参数的类型(Type):java.lang.String 2018-03-04 14:18:49 INFO ReflectMethodDemo:71 - 通过method.getParameterTypes()获取参数的类(Class):class java.lang.String 2018-03-04 14:18:49 INFO ReflectMethodDemo:77 - 通过method.getParameters()获取参数(Parameter)数组:java.lang.String arg0 2018-03-04 14:18:49 INFO ReflectMethodDemo:83 - 通过method.getGenericExceptionTypes()获取异常的类型(Type):java.lang.NullPointerException 2018-03-04 14:18:49 INFO ReflectMethodDemo:83 - 通过method.getGenericExceptionTypes()获取异常的类型(Type):java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:88 - 通过method.getExceptionTypes()获取异常的类(Class):class java.lang.NullPointerException 2018-03-04 14:18:49 INFO ReflectMethodDemo:88 - 通过method.getExceptionTypes()获取异常的类(Class):class java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:93 - 通过method.toString()获取方法的字符串描述:public java.lang.String pers.hanchao.reflect.common.User.getUsername() throws java.lang.NullPointerException,java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:94 - 通过method.toGenericString()获取方法的字符串描述(包括通用类型):public java.lang.String pers.hanchao.reflect.common.User.getUsername() throws java.lang.NullPointerException,java.lang.ArrayStoreException 2018-03-04 14:18:49 INFO ReflectMethodDemo:97 - 通过equals()比较两个方法是否相同:false 2018-03-04 14:18:49 INFO ReflectMethodDemo:99 - 通过method.isBridge()判断是否是桥方法:false 2018-03-04 14:18:49 INFO ReflectMethodDemo:101 - 通过method.isSynthetic()判断是否是合成方法:false 2018-03-04 14:18:49 INFO ReflectMethodDemo:104 - 通过method.isVarArgs()判断是否使用了可变参数:true 2018-03-04 14:18:49 INFO ReflectMethodDemo:107 - 通过method.getParameterCount()获取参数个数,setUsername = 1 2018-03-04 14:18:49 INFO ReflectMethodDemo:108 - 通过method.getParameterCount()获取参数个数,getUsername = 0 2018-03-04 14:18:49 INFO ReflectMethodDemo:111 - 通过method.getDefaultValue()获取默认返回值,setUsername = null 2018-03-04 14:18:49 INFO ReflectMethodDemo:112 - 通过method.getDefaultValue()获取默认返回值,getUsrMethod = null 2018-03-04 14:18:49 INFO ReflectMethodDemo:116 - 通过method.getTypeParameters()获取泛型方法的参数化类型(泛型),getUsrMethod()的参数化类型个数:0 2018-03-04 14:18:49 INFO ReflectMethodDemo:119 - 通过method.getTypeParameters()获取泛型方法的参数化类型(泛型),ReflectMethodDemo.test()的参数化类型:T 2018-03-04 14:18:49 INFO ReflectMethodDemo:122 - ////////////////////////////////////// Method注解信息获取 ///////////////////////////////////// 2018-03-04 14:18:49 INFO ReflectMethodDemo:125 - 通过method.getAnnotatedReturnType()获取被注解的返回值类型(组合类型):sun.reflect.annotation.AnnotatedTypeFactory$AnnotatedTypeBaseImpl@79fc0f2f 2018-03-04 14:18:49 INFO ReflectMethodDemo:127 - 通过annotatedType.getType()获取被注解的返回值类型中的返回值类型:class java.lang.String 2018-03-04 14:18:49 INFO ReflectMethodDemo:130 - 通过annotatedType.getAnnotations()获取被注解的返回值类型中的注解类型 2018-03-04 14:18:49 INFO ReflectMethodDemo:134 - 类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedParameterTypes() 2018-03-04 14:18:49 INFO ReflectMethodDemo:135 - 类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedExceptionTypes() 2018-03-04 14:18:49 INFO ReflectMethodDemo:136 - 类似于method.getAnnotatedReturnType()的还有: method.getAnnotatedReceiverType() 2018-03-04 14:18:49 INFO ReflectMethodDemo:141 - 通过method.getAnnotation(Annotation.class)获取指定的注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:142 - 通过method.getDeclaredAnnotation(Annotation.class)获取指定的注解 :@pers.hanchao.reflect.common.MyAnnotationB() 2018-03-04 14:18:49 INFO ReflectMethodDemo:146 - 通过method.getAnnotationsByType(MyAnnotation.class)获取一类注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:150 - 通过method.getDeclaredAnnotationsByType(MyAnnotation.class)获取一类注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:156 - 通过method.getAnnotations()获取全部注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:156 - 通过method.getAnnotations()获取全部注解: @pers.hanchao.reflect.common.MyAnnotationB() 2018-03-04 14:18:49 INFO ReflectMethodDemo:160 - 通过method.getDeclaredAnnotations()获取全部注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:160 - 通过method.getDeclaredAnnotations()获取全部注解: @pers.hanchao.reflect.common.MyAnnotationB() 2018-03-04 14:18:49 INFO ReflectMethodDemo:167 - 通过method.getParameterAnnotations()获取方法的所有参数注解(二维矩阵) 2018-03-04 14:18:49 INFO ReflectMethodDemo:175 - 第1个参数,第1个注解: @pers.hanchao.reflect.common.MyAnnotationA() 2018-03-04 14:18:49 INFO ReflectMethodDemo:175 - 第1个参数,第2个注解: @pers.hanchao.reflect.common.MyAnnotationB() 2018-03-04 14:18:49 INFO ReflectMethodDemo:175 - 第2个参数,第1个注解: @pers.hanchao.reflect.common.MyAnnotationB() 2018-03-04 14:18:49 INFO ReflectMethodDemo:180 - ////////////////////////////// Method 调用方法 /////////////////////////////// 2018-03-04 14:18:49 INFO ReflectMethodDemo:183 - 通过直接方法user.getUsername()获取 user.username = 张三 2018-03-04 14:18:49 INFO ReflectMethodDemo:185 - 通过反射方法method.invoke(user,args...)设置 user.username 2018-03-04 14:18:49 INFO ReflectMethodDemo:187 - 通过反射方法method.invoke(user,args...)获取 user.username = 张三丰 2018-03-04 14:18:49 INFO ReflectMethodDemo:190 - 私有成员变量:private void pers.hanchao.reflect.common.User.setUsernameByDefault() 2018-03-04 14:18:49 INFO ReflectMethodDemo:191 - 可以通过method.setAccessible(true)将私有方法private method设置为可访问的,从而操作私有方法 2018-03-04 14:18:49 INFO ReflectMethodDemo:193 - 操作私有成员方法 2018-03-04 14:18:49 INFO ReflectMethodDemo:195 - 查看私有成员方法调用结果:User{username='default', password='123456'}
4.总结
根据代码实例和运行结果,总结如下:Class对象与Method对象的相互转化
通过clazz.getMethod(name,args…)和clazz.getDeclaredMethod(name,args…)获取CLass对象的指定方法
通过clazz.getMethods()和clazz.getDeclaredMethods()获取CLass对象的全部方法
通过method.getDeclaringClass()获取当前Method对象所属的Class
Method信息获取
通过method.getModifiers()获取方法修饰符的int值
通过method.getName()获取方法名
通过method.getGenericReturnType()获取返回值的类型(Type),method.getReturnType()获取返回值的类(Class)
通过method.getGenericParameterTypes()获取参数的类型(Type),method.getParameterTypes()获取参数的类(Class)
通过method.getParameters()获取参数对象(Parameter[])数组
通过method.getGenericExceptionTypes()获取异常的类型(Type),method.getExceptionTypes()获取异常的类(Class)
通过method.toString()和method.toGenericString()获取方法的字符串描述
通过equals()比较两个方法是否相同
通过method.isBridge()判断是否是桥方法
通过method.isSynthetic()判断是否是合成方法
通过method.isVarArgs()判断是否使用了可变参数
通过method.getParameterCount()获取参数个数
通过method.getDefaultValue()获取默认返回值
通过method.getTypeParameters()获取泛型方法的参数化类型(泛型)
通过method.getAnnotatedXxxxType()获取被注解的类型(组合类型),Xxxx=[Return,Parameter,Exception,Receiver]
通过method.getAnnotation(Annotation.class)和method.getDeclaredAnnotation(Annotation.class)获取指定的注解
通过method.getAnnotationsByType(MyAnnotation.class)和method.getDeclaredAnnotationsByType(MyAnnotation.class)获取一组注解
通过method.getAnnotations()和method.getDeclaredAnnotations()获取全部注解
通过method.getParameterAnnotations()获取方法的所有参数注解(二维矩阵),数组元素表示第i个参数的第j个注解。
Method调用方法
通过method.invoke(user,args…)调用方法
可以通过method.setAccessible(true)将私有方法private method设置为可访问的,从而操作私有方法
备注:
有关获取Class对象的三种方式参见:Java反射02 : Class对象获取的三种方式和通过反射实例化对象的两种方式
有关getXxxx和getDeclaredXxxx参见:Java反射 : Declared的作用 ( 例如 : getMethods和getDeclaredMethods )
有关Class与Type参见: Java中Type接口与Class类的区别联系
有关参数化类型(泛型)参见系列:Java泛型学习系列-绪论
有关参数类(Parameter)参见后续章节:Java反射09 : 参数Parameter学习示例
使用成员方法Method进行反射编程的主要用法:通过成员方法Method进行方法(包括private)调用
相关文章推荐
- 深入理解 Java 反射:Method (成员方法)
- Java学习提要——"反射"获取方法信息(成员函数、成员变量 、构造函数)
- Java反射06 : 成员变量Field学习示例
- java反射学习笔记(3)---使用Class来获取方法、成员变量、构造函数信息
- JAVA反射(3) - Method成员方法解析
- 深入理解 Java 反射:Method (成员方法)
- Java 反射学习(三)成员方法的反射
- Java反射05 : 修饰符Modifier静态方法学习示例
- 深入理解 Java 反射:Method (成员方法)
- 黑马程序员——【Java反射学习】方法的反射/成员变量的反射/构造函数的反射
- Android(java)学习笔记109:通过反射获取成员变量和成员方法并且使用
- (JAVA自学笔记)成员方法的反射
- Java反射基本使用方法 示例
- java中用反射访问私有方法和私有成员[转]
- java 使用反射机制来获取私有方法和成员变量
- 黑马程序员--Java基础加强--16.利用反射操作泛型V【通过Constructor反射解析泛型构造方法】【通过Field反射解析泛型成员变量】【个人总结】
- Java的动态性支持学习二 - 反射机制 属性、方法、对象的操作
- JAVA反射中类的构造函数,成员变量,成员方法的使用
- 使用java反射中的getMethod,invoke方法调用对象方法的实例
- java反射学习--操作私有成员