我试图通过像这样的反射来获取包私有方法/字段:
for (Method m : getAllMethods(cls, withModifier(Modifier.STATIC))){
但它是空的。有没有办法按包私有过滤?
答案 0 :(得分:2)
要检索包私有方法,您需要查询所有方法,并使用public
,protected
或private
修饰符排除这些方法:
import org.reflections.ReflectionUtils;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.util.Set;
...
Set<Method> allMethods = ReflectionUtils.getAllMethods(Foo.class);
for (Method method : allMethods) {
boolean isPackagePrivate = !(Modifier.isPrivate(method.getModifiers()) || Modifier.isPublic(method.getModifiers()) || Modifier.isProtected(method.getModifiers()));
if (isPackagePrivate) {
System.out.println("package private method: " + method.getName());
}
}
字段相同:
Set<Field> allFields = ReflectionUtils.getAllFields(Foo.class);
for (Field field : allFields) {
boolean isPackagePrivate = !(Modifier.isPrivate(field.getModifiers()) || Modifier.isPublic(field.getModifiers()) || Modifier.isProtected(field.getModifiers()));
if (isPackagePrivate) {
System.out.println("package private field: " + field.getName());
}
}
com.google.guava:guava
使用Invokable围绕Method
(或Constructor
)提供更简单,更具可读性的API:
import com.google.common.reflect.Invokable
...
Invokable<?, Object> invokable = Invokable.from(method);
if (invokable.isPackagePrivate()) {
System.out.println("package private method: " + method.getName());
}
答案 1 :(得分:2)
for (Method m : getAllMethods(cls, ReflectionUtils.getAllMethods(cls, Predicates.not(withModifier(Modifier.PRIVATE)), Predicates.not(withModifier(Modifier.PUBLIC)), Predicates.not(withModifier(Modifier.PROTECTED)))))
{
// DO STUFF
}
我使用以下内容来测试上述内容。 MyClass
包含5种方法;每个访问修饰符一个,一个静态:
public class MyClass
{
public void method1()
{
System.out.println("method1() invoked");
}
private void method2()
{
System.out.println("method2() invoked");
}
protected void method3()
{
System.out.println("method3() invoked");
}
void method4()
{
System.out.println("method4() invoked");
}
public static void method5()
{
System.out.println("method5() invoked");
}
}
我的测试班:
import static org.reflections.ReflectionUtils.withModifier;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.util.Set;
import org.reflections.ReflectionUtils;
import accessmodifier.bar.MyClass;
import com.google.common.base.Predicates;
public class ReflectionTest
{
public static void main(String[] args)
{
Class<MyClass> cls = MyClass.class;
Set<Method> privateMethods = ReflectionUtils.getAllMethods(cls, withModifier(Modifier.PRIVATE));
Set<Method> protectedMethods = ReflectionUtils.getAllMethods(cls, withModifier(Modifier.PROTECTED));
Set<Method> publicMethods = ReflectionUtils.getAllMethods(cls, withModifier(Modifier.PUBLIC));
Set<Method> defaultMethods = ReflectionUtils.getAllMethods(cls, Predicates.not(withModifier(Modifier.PRIVATE)), Predicates.not(withModifier(Modifier.PUBLIC)), Predicates.not(withModifier(Modifier.PROTECTED)));
Set<Method> staticMethods = ReflectionUtils.getAllMethods(cls, withModifier(Modifier.STATIC));
System.out.println("Private Methods");
for (Method m : privateMethods)
System.out.println(m.getName());
System.out.println("\nProtected Methods");
for (Method m : protectedMethods)
System.out.println(m.getName());
System.out.println("\nPublic Methods");
for (Method m : publicMethods)
System.out.println(m.getName());
System.out.println("\nPackage-Private Methods");
for (Method m : defaultMethods)
System.out.println(m.getName());
System.out.println("\nStatic Methods");
for (Method m : staticMethods)
System.out.println(m.getName());
}
}
计划输出
Private Methods
method2
Protected Methods
method3
Public Methods
method1
method5
Package-Private Methods
method4
Static Methods
method5
<强>更新强> 如果您希望能够调用可访问的方法(例如package-private),则必须执行以下操作:
m.setAccessible(true); // bypass access
try
{
m.invoke(new MyClass(), null); // invoke method (you have to know parameter types and pass them if needed. Use *Method.getParameter...()* methods for that.
}
catch (IllegalAccessException | IllegalArgumentException
| InvocationTargetException e)
{
e.printStackTrace();
}