java.lang.reflect.Method类提供了访问Method的修饰符、返回类型、参数、注解和抛出异常信息的API。它也被用来调用Methods。
下面的类图显示java.lang.reflect.Method类提供了访问Method的修饰符、返回类型、参数、注释和抛出的异常信息的API。
*获取Method类型信息
这个例子说明了如何在一个给定的类中枚举所有声明的Method,并检索给定名称的所有Method的返回、参数和异常类型。
public static void reflectionMethodExamples() {
final String fmt = "%24s: %s%n";
try {
Class<?> c = Class.forName("com.javaguides.reflection.methods.Employee");
Method[] allMethods = c.getDeclaredMethods();
for (Method m : allMethods) {
out.format("%s%n", m.toGenericString());
out.format(fmt, "ReturnType", m.getReturnType());
out.format(fmt, "GenericReturnType", m.getGenericReturnType());
Class<?>[] pType = m.getParameterTypes();
Type[] gpType = m.getGenericParameterTypes();
for (int i = 0; i < pType.length; i++) {
out.format(fmt, "ParameterType", pType[i]);
out.format(fmt, "GenericParameterType", gpType[i]);
}
Class<?>[] xType = m.getExceptionTypes();
Type[] gxType = m.getGenericExceptionTypes();
for (int i = 0; i < xType.length; i++) {
out.format(fmt, "ExceptionType", xType[i]);
out.format(fmt, "GenericExceptionType", gxType[i]);
}
}
// production code should handle these exceptions more gracefully
} catch (ClassNotFoundException x) {
x.printStackTrace();
}
}
输出:
public java.lang.String com.javaguides.reflection.methods.Employee.getName()
ReturnType: class java.lang.String
GenericReturnType: class java.lang.String
public int com.javaguides.reflection.methods.Employee.getId()
ReturnType: int
GenericReturnType: int
public void com.javaguides.reflection.methods.Employee.setName(java.lang.String)
ReturnType: void
GenericReturnType: void
ParameterType: class java.lang.String
GenericParameterType: class java.lang.String
private int com.javaguides.reflection.methods.Employee.getAge()
ReturnType: int
GenericReturnType: int
public void com.javaguides.reflection.methods.Employee.setId(int)
ReturnType: void
GenericReturnType: void
ParameterType: int
GenericParameterType: int
。
MethodParameterSpy例子说明了如何检索一个给定类的所有构造函数和Methods的形式参数的名称。这个例子还打印了关于每个参数的其他信息。
package com.javaguides.reflection.methods;
import static java.lang.System.out;
import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
public class MethodParameterSpy {
private static final String fmt = "%24s: %s%n";
// for the morbidly curious
<E extends RuntimeException> void genericThrow() throws E {}
public static void printClassConstructors(Class c) {
Constructor[] allConstructors = c.getConstructors();
out.format(fmt, "Number of constructors", allConstructors.length);
for (Constructor currentConstructor : allConstructors) {
printConstructor(currentConstructor);
}
Constructor[] allDeclConst = c.getDeclaredConstructors();
out.format(fmt, "Number of declared constructors",
allDeclConst.length);
for (Constructor currentDeclConst : allDeclConst) {
printConstructor(currentDeclConst);
}
}
public static void printClassMethods(Class c) {
Method[] allMethods = c.getDeclaredMethods();
out.format(fmt, "Number of methods", allMethods.length);
for (Method m : allMethods) {
printMethod(m);
}
}
public static void printConstructor(Constructor c) {
out.format("%s%n", c.toGenericString());
Parameter[] params = c.getParameters();
out.format(fmt, "Number of parameters", params.length);
for (int i = 0; i < params.length; i++) {
printParameter(params[i]);
}
}
public static void printMethod(Method m) {
out.format("%s%n", m.toGenericString());
out.format(fmt, "Return type", m.getReturnType());
out.format(fmt, "Generic return type", m.getGenericReturnType());
Parameter[] params = m.getParameters();
for (int i = 0; i < params.length; i++) {
printParameter(params[i]);
}
}
public static void printParameter(Parameter p) {
out.format(fmt, "Parameter class", p.getType());
out.format(fmt, "Parameter name", p.getName());
out.format(fmt, "Modifiers", p.getModifiers());
out.format(fmt, "Is implicit?", p.isImplicit());
out.format(fmt, "Is name present?", p.isNamePresent());
out.format(fmt, "Is synthetic?", p.isSynthetic());
}
public static void main(String... args) {
try {
printClassConstructors(Class.forName("com.javaguides.reflection.methods.Employee"));
printClassMethods(Class.forName("com.javaguides.reflection.methods.Employee"));
} catch (ClassNotFoundException x) {
x.printStackTrace();
}
}
}
输出:
Number of constructors: 1
public com.javaguides.reflection.methods.Employee()
Number of parameters: 0
Number of declared constructors: 1
public com.javaguides.reflection.methods.Employee()
Number of parameters: 0
Number of methods: 5
public java.lang.String com.javaguides.reflection.methods.Employee.getName()
Return type: class java.lang.String
Generic return type: class java.lang.String
public int com.javaguides.reflection.methods.Employee.getId()
Return type: int
Generic return type: int
public void com.javaguides.reflection.methods.Employee.setName(java.lang.String)
Return type: void
Generic return type: void
Parameter class: class java.lang.String
Parameter name: arg0
Modifiers: 0
Is implicit?: false
Is name present?: false
Is synthetic?: false
public void com.javaguides.reflection.methods.Employee.setId(int)
Return type: void
Generic return type: void
Parameter class: int
Parameter name: arg0
Modifiers: 0
Is implicit?: false
Is name present?: false
Is synthetic?: false
private int com.javaguides.reflection.methods.Employee.getAge()
Return type: int
Generic return type: int
。
有几个修饰符可能是Method声明的一部分。
package com.javaguides.reflection.methods;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import static java.lang.System.out;
public class MethodModifierSpy {
private static int count;
private static synchronized void inc() {
count++;
}
private static synchronized int cnt() {
return count;
}
public static void main(String... args) {
try {
Class<?> c = Class.forName("java.lang.Object");
Method[] allMethods = c.getDeclaredMethods();
for (Method m : allMethods) {
if (!m.getName().equals("wait")) {
continue;
}
out.format("%s%n", m.toGenericString());
out.format(" Modifiers: %s%n", Modifier.toString(m.getModifiers()));
out.format(" [ synthetic=%-5b var_args=%-5b bridge=%-5b ]%n", m.isSynthetic(), m.isVarArgs(),
m.isBridge());
inc();
}
out.format("%d matching overload%s found%n", cnt(), (cnt() == 1 ? "" : "s"));
// production code should handle this exception more gracefully
} catch (ClassNotFoundException x) {
x.printStackTrace();
}
}
}
输出:
public final void java.lang.Object.wait() throws java.lang.InterruptedException
Modifiers: public final
[ synthetic=false var_args=false bridge=false ]
public final void java.lang.Object.wait(long,int) throws java.lang.InterruptedException
Modifiers: public final
[ synthetic=false var_args=false bridge=false ]
public final native void java.lang.Object.wait(long) throws java.lang.InterruptedException
Modifiers: public final native
[ synthetic=false var_args=false bridge=false ]
3 matching overloads found
让我们首先创建Employee.java类,然后我们将在Employee类上应用所有的反射API Methods。
package com.javaguides.reflection.methods;
public class Employee {
private int id;
private String name;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
我们可以使用getMethod()来获取一个类的公共Method,我们需要传递Method名称和Method的参数类型。如果在类中没有找到该Method,反射API会在超类中寻找该Method。
Class<?> concreteClass = Class.forName("com.javaguides.reflection.methods.Employee");
Method method = concreteClass.getMethod("getName");
System.out.println(method.getName());
Method method2 = concreteClass.getMethod("getId", String.class);
System.out.println(method2.getName());
Method putMethod = Class.forName("java.util.HashMap").getMethod("put", Object.class, Object.class);
// get method parameter types, prints "[class java.lang.Object, class
// java.lang.Object]"
System.out.println(Arrays.toString(putMethod.getParameterTypes()));
// get method return type, return "class java.lang.Object", class
// reference for void
System.out.println(putMethod.getReturnType());
// get method modifiers
System.out.println(Modifier.toString(method.getModifiers()));
输出:
getName
setId
[class java.lang.Object, class java.lang.Object]
class java.lang.Object
public
。
我们可以使用Method对象的invoke()Method来调用一个Method,在下面的示例代码中,我们使用反射来调用HashMap上的putMethod。
Method method = Class.forName("java.util.HashMap").getMethod("put", Object.class, Object.class);
Map<String, String> hm = new HashMap<>();
method.invoke(hm, "key", "value");
System.out.println(hm); // prints {key=value}
getMethods() Method 返回该类的公共Methods数组,包括它的超类和超接口的公共Methods。
Class<?> concreteClass = Class.forName("com.javaguides.reflection.methods.Employee");
Method[] methods = concreteClass.getMethods();
for (Method method : methods) {
System.out.println(method.getName());
}
输出:
getName
getId
setName
setId
wait
wait
wait
equals
toString
hashCode
getClass
notify
notifyAll
https://docs.oracle.com/javase/tutorial/reflect/class/index.html
https://docs.oracle.com/javase/8/docs/api/java/lang/reflect/package-summary.html
https://docs.oracle.com/javase/8/docs/api/java/lang/reflect/Method.html
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://www.javaguides.net/2018/07/java-reflection-for-methods.html
内容来源于网络,如有侵权,请联系作者删除!