1.反射系列:Method

本文深入解析Java反射API中的Method类,详细介绍了通过反射获取方法信息的过程,包括方法的注解、修饰符、泛型参数、返回值、名称、参数及异常。并通过一个具体示例演示了如何使用反射调用方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

https://blog.youkuaiyun.com/zhangquanit/article/details/52927216
Method 提供关于类或接口上单独某个方法(以及如何访问该方法)的信息。
一个完整方法包含的属性有:
方法上使用的注解、方法的修饰符、方法上定义的泛型参数、方法的返回值、方法名称、方法参数(泛型、注解)、方法抛出的异常。
比如下面这个方法:

@MyAnnotation
public <T> boolean add(List<T> list,T...params)throws RuntimeException,Exception{
	if(null==list){
		throw new RuntimeException("list=null");
	}
	
	if(null==params){
		return false;
	}
	//将参数添加到List集合中
	if(null!=params){
		for(T t:params){
			list.add(t);
		}
	}
	return true;
}

注解:@MyAnnotation
修饰符:public
泛型参数:T
返回值:boolean
方法名:add
方法参数(泛型、注解):List list,T…params
抛出的异常:RuntimeException,Exception

---------------------
package reflect;
 
import java.lang.annotation.Annotation;
import java.lang.reflect.GenericArrayType;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.lang.reflect.TypeVariable;
import java.lang.reflect.WildcardType;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
 
/**
 * @author zhangquanit
 */
public class MethodTest {
 
	/**
	 * 一个完整方法包含的属性有: 方法上使用的注解、方法的修饰符、方法上定义的泛型参数、方法的返回值、方法名称、方法参数(泛型、注解)、方法抛出的异常
	 */
	@MyAnnotation
	private <T> boolean add(@MyAnnotation List<T> list, T... params) throws RuntimeException,
			Exception {
		if (null == list) {
			throw new RuntimeException("list=null");
		}
 
		if (null == params) {
			return false;
		}
		// 将参数添加到List集合中
		if (null != params) {
			for (T t : params) {
				list.add(t);
			}
		}
		return true;
	}
 
	public static void main(String[] args) throws Exception {
		// 获取Method
		MethodTest obj = new MethodTest();
		Class<? extends MethodTest> clazz = obj.getClass();
 
		Method method = clazz.getDeclaredMethod("add", List.class,
				Object[].class);
		if (!method.isAccessible()) {
			method.setAccessible(true);
		}
        //获取方法基本信息
		getMethodInfo(method);
		
		// 调用方法
		List<String> arrayList = new ArrayList<String>();
		method.invoke(obj, arrayList, new String[] { "1", "2" });
		System.out.println(arrayList);//[1,2]
		
		//方法定义所在的类
		Class<?> declaringClass = method.getDeclaringClass();
		
		// 如果此方法是 bridge 方法,则返回 true;
		boolean bridge = method.isBridge();
		//如果该方法是public非抽象非静态,且定义在接口中,则返回true
		boolean default1 = method.isDefault(); //false
		//如果此方法为复合方法,则返回 true;
		boolean synthetic = method.isSynthetic();//false
		// 如果将此方法的参数带有可变参数,则返回 true
		boolean varArgs = method.isVarArgs(); //true
		
		
		
	}
 
	private static void getMethodInfo(Method method) {
		// 1、获取方法上的注解
		boolean annotationPresent = method
				.isAnnotationPresent(MyAnnotation.class);
		if (annotationPresent) {
			MyAnnotation myAnnotation = method
					.getDeclaredAnnotation(MyAnnotation.class);
		}
		// 2、方法的修饰符
		int modifiers = method.getModifiers();
		String modify = Modifier.toString(modifiers);// private
		// 3、方法上定义的泛型参数
		TypeVariable<Method>[] typeParameters = method.getTypeParameters();// [T]
		// 4、方法的返回值
		Class<?> returnType = method.getReturnType();// boolean
		Type genericReturnType = method.getGenericReturnType();// boolean
		// 5、方法名称
		String name = method.getName();
		// 6、方法参数
		int parameterCount = method.getParameterCount();// 参数个数 2
		// 方法参数——泛型
		Class<?>[] parameterTypes = method.getParameterTypes();
		// 打印 [interface java.util.List, class [Ljava.lang.Object;]
		Type[] genericParameterTypes = method.getGenericParameterTypes();
		// 打印 [java.util.List<T>, T[]]
		for (Type type : genericParameterTypes) {
			if (type instanceof ParameterizedType) { // 参数类型
				System.out.println("ParameterizedType类型:" + type);
				ParameterizedType parameterizedType = (ParameterizedType) type;
				Type[] actualTypeArguments = parameterizedType
						.getActualTypeArguments();
				System.out.println("实际参数为:"
						+ Arrays.toString(actualTypeArguments));
				for (Type actualType : actualTypeArguments) {
					if (actualType instanceof WildcardType) {
						WildcardType wildcardType = (WildcardType) actualTypeArguments[0];
						System.out.println("实际参数为WildcardType类型:"
								+ wildcardType.getUpperBounds());
					} else if (actualType instanceof Class) {
						System.out.println("实际参数为Class类型:" + actualType);
					}
				}
 
			} else if (type instanceof GenericArrayType) { // 泛型数组类型 T[]
				GenericArrayType genericArrayType = (GenericArrayType) type;
				System.out.println("GenericArrayType类型:"
						+ genericArrayType.getGenericComponentType());//T
			} else if (type instanceof TypeVariable) { // 泛型变量
				System.out.println("TypeVariable类型:" + type);
			} else if (type instanceof Class) { //
				System.out.println("Class类型:" + type);
			}
		}
		/*
		 * 方法有2个参数,第一个参数list为ParameterizedType,实际参数为T,
		 * 第二个参数为GenericArrayType泛型数组类型T[],数组元素类型为T
		 */
		
		//方法参数——注解   第一个参数使用了注解
		Annotation[][] parameterAnnotations = method.getParameterAnnotations();
		Annotation myAnnotation=parameterAnnotations[0][0];
		//打印 @reflect.MyAnnotation(intValue=0)
		
 
		// 7、方法抛出的异常
		Class<?>[] exceptionTypes = method.getExceptionTypes();
		// 打印 [class java.lang.RuntimeException, class java.lang.Exception]
		Type[] genericExceptionTypes = method.getGenericExceptionTypes();
		// 打印 [class java.lang.RuntimeException, class java.lang.Exception]
 
	}
}
异常描述: java.lang.ArrayStoreException: sun.reflect.annotation.TypeNotPresentExceptionProxy java.lang.ArrayStoreException: sun.reflect.annotation.TypeNotPresentExceptionProxy at sun.reflect.annotation.AnnotationParser.parseClassArray(AnnotationParser.java:724) at sun.reflect.annotation.AnnotationParser.parseArray(AnnotationParser.java:531) at sun.reflect.annotation.AnnotationParser.parseMemberValue(AnnotationParser.java:355) at sun.reflect.annotation.AnnotationParser.parseAnnotation2(AnnotationParser.java:286) at sun.reflect.annotation.AnnotationParser.parseAnnotations2(AnnotationParser.java:120) at sun.reflect.annotation.AnnotationParser.parseAnnotations(AnnotationParser.java:72) at java.lang.reflect.Executable.declaredAnnotations(Executable.java:599) at java.lang.reflect.Executable.declaredAnnotations(Executable.java:597) at java.lang.reflect.Executable.getDeclaredAnnotations(Executable.java:588) at java.lang.reflect.Method.getDeclaredAnnotations(Method.java:630) at org.springframework.core.annotation.AnnotationsScanner.getDeclaredAnnotations(AnnotationsScanner.java:453) at org.springframework.core.annotation.AnnotationsScanner.isKnownEmpty(AnnotationsScanner.java:491) at org.springframework.core.annotation.TypeMappedAnnotations.from(TypeMappedAnnotations.java:251) at org.springframework.core.annotation.MergedAnnotations.from(MergedAnnotations.java:351) at org.springframework.core.annotation.MergedAnnotations.from(MergedAnnotations.java:330) at org.springframework.core.annotation.AnnotatedElementUtils.findAnnotations(AnnotatedElementUtils.java:800) at org.springframework.core.annotation.AnnotatedElementUtils.hasAnnotation(AnnotatedElementUtils.java:541)怎么解决
03-28
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值