无论参数如何都要获取方法

时间:2014-10-09 22:19:11

标签: java reflection

我试图获取方法,无论该方法采用什么参数(截至目前没有方法重载,将来也不会)。我能提出的唯一可行解决方案是

private Method getMethod(Class<?> clas, String methodName) {
    try {
        Method[] methods = clas.getMethods();
        for (Method method : methods) {
            if (method.getName().equalsIgnoreCase(methodName)) {
                return method;
            }
        }
    } catch (SecurityException e) {
        e.printStackTrace();
    }
    return null;
}

我想问的是,有什么方法可以获取方法而不管其参数如何?我正在查看clas.getMethod ("methodName", parameters),如果我在其中提供null,它将尝试获取没有参数的方法。哪个不是没有案例。

有什么想法吗?

修改 谢谢大家的意见。就我而言,我知道无论如何都只有一种方法。我使用ignoreCase的原因是因为输入来自开发人员(在其他团队中),他将提供名称作为硬编码字符串。因此,为了防止事情泄漏,我采用了安全的方法。

4 个答案:

答案 0 :(得分:1)

没有。你完成它的方式就是你要走的路。方法由其签名标识,签名包括名称和参数类型。

答案 1 :(得分:0)

这是一个解决方案,它检索具有指定类和方法名称的所有方法,而不管方法的参数如何:

public class Test
{
    private class Foo
    {
        public void bar()
        {

        }

        public void bar(String s)
        {

        }

        public void goo()
        {

        }
    }

    private static Method[] getMethods(Class<?> clazz, String methodName)
    {
        List<Method> methods = new ArrayList<Method>();

        Method[] declaredMethods = clazz.getDeclaredMethods();

        for (Method declaredMethod: declaredMethods)
        {
            if (declaredMethod.getName().equals(methodName))
            {
                methods.add(declaredMethod);
            }
        }

        return methods.toArray(new Method[methods.size()]);
    }

    public static void main(String[] args)
    {
        Method[] methods = getMethods(Foo.class, "bar");

        System.out.println(Arrays.toString(methods));
    }
}

这会生成以下输出:

[public void com.example.Test$Foo.bar(java.lang.String), public void com.example.Test$Foo.bar()]

答案 2 :(得分:0)

你做得很好。这与我四年前处理的类似问题的解决方案基本相同,创建了一种在Java中创建回调方法的方法。我的Callback类的构造函数是:

public Callback(Class<?> clazz, String methodName, Object parentObj) {
    // Find a method with the matching name
    Method[] allMethods;
    try { allMethods = clazz.getMethods(); }
    catch(SecurityException se) { allMethods = new Method[0]; }

    int count = 0;
    Method single = null;
    for(Method m : allMethods) {
        if(m.getName().equals(methodName)) {
            single = m;
            count++;
        }

        // Can't have more than one instance
        if(count > 1)
            throw new IllegalArgumentException(clazz.getName()
                + " has more than one method named " + methodName);
    }
    if(count == 0) // No instances found
        throw new IllegalArgumentException(clazz.getName()
            + " has no method named " + methodName);

    this.parentObj = parentObj;
    this.method = single;
    this.parameters = single.getParameterTypes();
}

public Callback(
    Class<?> clazz,
    String methodName,
    Object parentObj,
    Class<?>...parameters)
{
    try { this.method = clazz.getMethod(methodName, parameters); }
    catch(NoSuchMethodException nsme) { nsme.printStackTrace(); }
    catch(SecurityException se) { se.printStackTrace(); }

    this.parentObj = parentObj;
    this.parameters = parameters;
}

我的Callback类在Java 8时代已经不再有用,但当时java中“回调”的唯一真正方法是匿名接口实现,这对于我的用例。

正如您在第一个构造函数中看到的,如果它找到多个具有相同名称的方法,则会抛出异常。

答案 3 :(得分:0)

Using java streams there is a really short method of finding a method, the first match, by its name only:

Stream.of(type.getMethods())
.filter((m) -> m.getName().equals(searchedName))
.findFirst()
.get();

I think this is a short and readable possibility in this case.