反射时Java参数类型不匹配

时间:2014-06-24 12:56:58

标签: java reflection

我正在尝试运行一些方法,我从另一个jar加载,返回一个整数,然后我想将它返回到另一个类并将其传递给我的逻辑。

我的方法加载类很简单,就像这样:

public class ModuleLoader {

    private Class<?> cls;

    public void initializeCommandModule(Module m) throws Exception {
        URL url = this.getURL(m.getJar());
        this.cls = this.loadClass(m.getMainClass(), url);
    }

    public int execute(Module m, ArrayList<String> args) throws Exception {
        Method method = this.cls.getDeclaredMethod("execute", ArrayList.class);
        return (int) method.invoke(this.cls.newInstance(), 1);
    }

    public int respond(ArrayList<String> args) throws Exception {
        Method method = this.cls.getDeclaredMethod("response", ArrayList.class);
        return (int) method.invoke(this.cls.newInstance(), 1);
    }

    private Class<?> loadClass(String cls, URL url) throws ClassNotFoundException, IOException {
        URLClassLoader loader = new URLClassLoader(new URL[]{url});
        Class<?> toReturn = loader.loadClass(cls);
        loader.close();

        return toReturn;
    }

    private URL getURL(String jar) throws MalformedURLException {
        return new File(jar).toURI().toURL();
    }

}

看一下execute(Module m, ArrayList<String> args)方法,这一行会引发错误:

    return (int) method.invoke(this.cls.newInstance());

我加载的jar库看起来像这样:

public class Test {

    public int execute(ArrayList<String> i) {
        System.out.println("Hello world!");
        return 0;
    }

}

为什么当我运行该方法时,我会抛出以下异常?

Exception in thread "main" java.lang.IllegalArgumentException: argument type mismatch
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    at java.lang.reflect.Method.invoke(Unknown Source)
    at ben.console.modules.ModuleLoader.execute(ModuleLoader.java:24)
    at ben.console.CommandProcessor.process(CommandProcessor.java:37)
    at ben.console.Console.listen(Console.java:25)
    at ben.console.Console.main(Console.java:31)

感谢您的建议!

5 个答案:

答案 0 :(得分:3)

您忘记将参数传递给方法调用。

return (int) method.invoke(this.cls.newInstance(), myArrayList);

您也可以使用null参数调用:

return (int) method.invoke(this.cls.newInstance(), (Object[])null);

答案 1 :(得分:1)

execute()方法中,您有

return (int) method.invoke(this.cls.newInstance());

我想你想要

return (int) method.invoke(this, args);

respond()同样,

Method method = this.cls.getDeclaredMethod("response", ArrayList.class);
return (int) method.invoke(this.cls.newInstance(), 1);

应该是

return (int) method.invoke(this, args);

您可能会发现我的blog post here有帮助。

答案 2 :(得分:1)

据我所知,你获取的方法接受ArrayList类型的一个参数:

Method method = this.cls.getDeclaredMethod("execute", ArrayList.class);

但是后来尝试使用我无法识别的类型的参数调用它,显然不是ArrayList

(int) method.invoke(this.cls.newInstance()); 

this.cls.newInstance()的类型是什么? cls的值在方法initializeCommandModule()中分配如下:

this.cls = this.loadClass(m.getMainClass(),url);

其中mModule。我不知道Module是什么,因此不知道getMainClass()返回什么。

答案 3 :(得分:0)

您也可以尝试将其转换为整数。我遇到了同样的问题,并且一直在拔头发。使用Integer.parseInt可以达到目的。我希望这会有所帮助。

这是示例代码:

String num = "1";
int result = Integer.parseInt(num);         
System.out.println(result);

答案 4 :(得分:0)

如果您加载具有不同 ClassLoader 的方法类和参数类,则会发生此错误