java 方法中带有超类参数的Java getMethod

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2580665/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-29 21:53:34  来源:igfitidea点击:

Java getMethod with superclass parameters in method

javareflection

提问by Jonathon Faust

Given:

鉴于:

class A
{
    public void m(List l) { ... }
}

Let's say I want to invoke method mwith reflection, passing an ArrayList as the parameter to m:

假设我想m通过反射调用方法,将 ArrayList 作为参数传递给m

List myList = new ArrayList();
A a = new A();
Method method = A.class.getMethod("m", new Class[] { myList.getClass() });
method.invoke(a, Object[] { myList });

The getMethodon line 3 will throw NoSuchMethodExceptionbecause the runtime type of myList is ArrayList, not List.

getMethod3 行将抛出,NoSuchMethodException因为 myList 的运行时类型是 ArrayList,而不是 List。

Is there a good generic way around this that doesn't require knowledge of class A's parameter types?

是否有一个很好的通用方法来解决这个问题,不需要了解 A 类的参数类型?

回答by Bozho

If you know the type is List, then use List.classas argument.

如果您知道类型是List,则List.class用作参数。

If you don't know the type in advance, imagine you have:

如果您事先不知道类型,请想象您有:

public void m(List l) {
 // all lists
}

public void m(ArrayList l) {
  // only array lists
}

Which method should the reflection invoke, if there is any automatic way?

如果有任何自动方式,反射应该调用哪个方法?

If you want, you can use Class.getInterfaces()or Class.getSuperclass()but this is case-specific.

如果需要,您可以使用Class.getInterfaces()or ,Class.getSuperclass()但这是特定于案例的。

What you can do here is:

你可以在这里做的是:

public void invoke(Object targetObject, Object[] parameters,
        String methodName) {
    for (Method method : targetObject.getClass().getMethods()) {
        if (!method.getName().equals(methodName)) {
            continue;
        }
        Class<?>[] parameterTypes = method.getParameterTypes();
        boolean matches = true;
        for (int i = 0; i < parameterTypes.length; i++) {
            if (!parameterTypes[i].isAssignableFrom(parameters[i]
                    .getClass())) {
                matches = false;
                break;
            }
        }
        if (matches) {
            // obtain a Class[] based on the passed arguments as Object[]
            method.invoke(targetObject, parametersClasses);
        }
    }
}

回答by user207421

See java.beans.Expression and java.beans.Statement.

请参阅 java.beans.Expression 和 java.beans.Statement。

回答by Matt Ball

Instead of myList.getClass(), why not just pass in List.class? That iswhat your method is expecting.

相反myList.getClass(),为什么不直接传入List.class?这就是您的方法所期望的。

回答by Sean Owen

I'm guessing you want getDeclaredMethods(). Here is an example. You can dig through the list of methods and pick the one you want by name. Whether or not this is robust or a good idea is another question.

我猜你想getDeclaredMethods()。这是一个例子。您可以浏览方法列表并按名称选择您想要的方法。这是否可靠或一个好主意是另一个问题。