2015-09-03 2 views
7

Ich muss etwas sehr grundlegendes vermissen. Wenn ich versuche, während eines Methodenaufrufs ein Array irgendeiner Art zu übergeben, erhalte ich einen Fehler. Aber wenn ich es normalerweise mache, funktioniert es.IllegalArgumentException beim Übergeben eines Array als Parameter während des Methodenaufrufs

Dies ist der komplette Code,

import java.lang.reflect.Method; 

public class Main { 
    public static void main(String[] args) throws Exception { 

     // Normal 
     MyClass.sayHello(new String[] {"StackOverflow"}); 

     // Reflection 
     Method m = MyClass.class.getMethod("sayHello", String[].class); 
     m.invoke(null, new String[]{"StackOverflow"}); 
    } 

    static class MyClass { 
     public static void sayHello(String[] args) { 
      System.out.println("Hello " + args[0]); 
     } 
    } 
} 

Die Exception

Exception in thread "main" java.lang.IllegalArgumentException: argument type mismatch 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 
at java.lang.reflect.Method.invoke(Method.java:497) 
at Main.main(Main.java:11) 

String... nicht funktioniert entweder btw geworfen ausfällt.

Antwort

7

Das Problem ist, dass der zweite Parameter invoke ein Array von Argumenten gemeint ist - Sie geben nur ein einzelnes Argument an.

In den meisten Fällen wäre das in Ordnung, da der zweite Parameter von Method.invoke ein Varargs-Parameter ist, aber da Ihr Argument bereits ein mit Object[] kompatibles Array ist, erstellt der Compiler kein Wrapper-Array. Ich würde erwarten, dass Sie eine Kompilierung Zeit wie diese Warnung erhalten:

Main.java:11: warning: non-varargs call of varargs method with inexact argument type for 
         last parameter; 
     m.invoke(null, new String[]{"StackOverflow"}); 
        ^
    cast to Object for a varargs call 
    cast to Object[] for a non-varargs call and to suppress this warning 

Sie könnten entweder explizit ein Array erstellen das Argument Einwickeln oder werfen das Argument Object so dass der Compiler selbst wickeln muss:

// Creates the wrapper array explicitly 
m.invoke(null, new Object[] { new String[] { "StackOverflow" } }); 

oder

// Compiler creates the wrapper array because the argument type is just Object 
m.invoke(null, (Object) new String[] { "StackOverflow" }); 
+0

TLDR: Wie immer RTFD – mvd

+0

Ja, ich habe die gleiche Warnung. Es macht keinen Sinn, warum Java ein Array von Array-Argumenten benötigt, aber es funktioniert. Vielen Dank! – TomTom

+0

@ TomTom: Es macht Sinn: Es braucht ein Array, weil es mehrere Argumente geben kann. Das einzige Element dieses Arrays ist selbst ein Array, da der Parameter der Methode ein Array ist. Versuchen Sie, der Methode einen weiteren Parameter hinzuzufügen, und es wird mehr Sinn ergeben. Und in Zukunft * Warnungen * nie ignorieren :) –