2009-11-01 10 views
43

consideri dichiarazione del metodo:varargs e '...' argomento

String.format(String, Object ...) 

L'argomento Object ... è solo un riferimento ad un array di Object s. C'è un modo per usare questo metodo con un riferimento ad un effettivo array Object? Se passo in un Object matrice all'argomento ... - sarà il valore di argomento risultante tramite una matrice bidimensionale - perché un Object[] è essa stessa Object:

Object[] params = ....; // Make the array (for example based on user-input) 
String s = String.format("%S has %.2f euros", params); 

Quindi il primo componente della matrice (che è utilizzato nel metodo String.format), sarà un array ed egli genererà:

[class.getName() + "@" + Integer.toHexString(hashCode())] 

e quindi un errore perché la dimensione dell'array è 1.

La sequenza in grassetto è la vera domanda.
Questa è una seconda domanda: Un array/parametro ... ha un nome?

+1

Scusa, ho dovuto testarlo prima di chiedere ... Penso di aver avuto questo problema molto tempo fa. –

risposta

52

Dal docs on varargs:

I tre periodi dopo tipo finale del parametro indicano che l'argomento finale può essere passato come array o come una sequenza di argomenti.

Quindi è possibile passare più argomenti o un array.

I seguenti funziona bene:

class VarargTest { 
    public static void main(String[] args) { 
    Object[] params = {"x", 1.2345f}; 
    String s = String.format("%s is %.2f", params); 
    System.out.println(s); // Output is: x is 1.23 
    } 
} 
+1

Quindi, se si desidera chiamare il metodo con un singolo argomento e si verifica che sia un array, è necessario inserirlo in un altro. 'metodo (nuovo Object [] {array});' –

+8

o do 'method ((Object) array)', che eseguirà l'auto-wrapping – naiad

+0

Sto meglio di prima ho visto queste spiegazioni sui parametri vararg, eppure continuo a proprio non capisco. – Sizons

11

Si può solo passare una matrice:

public void foo(String... args) { 
} 

String args[] = new String[10]; 
foo(args); 
+0

Non mi preoccuperò nemmeno di aggiungere la mia risposta, modificare in "... è noto come vararg o argomenti variabili e richiede 0..n elementi di elementi specificati" o qualcosa del genere. – Esko

8

La situazione si sta descrivendo sta per essere abbastanza rara: la maggior parte del tempo, i tuoi articoli varargs sarà String s, o numeri, o Widget s .. sarà insolito per loro essere Object s (che potrebbe essere qualsiasi cosa) o matrici.

Ma se l'argomento varargs è un mazzo di Object s o un tipo di matrice, quindi la tua domanda si pone: è possibile passare un singolo array e poi come sarà il compilatore sapere se si intende far passare una matrice (quello che hai fornito), o una serie di 1 oggetto che dovrebbe essere inserito in un array per te?

Un test rapido mostra la risposta:

public class TestClass { 
    public static void main(String[] args) { 
     Object anObject = new Object(); 
     Object[] anArray = new Object[] {anObject, anObject}; 
     System.out.println("object1 = " + anObject); 
     System.out.println("array1 = " + anArray); 
     takesArgs(); 
     takesArgs(anObject, anObject); 
     takesArgs(anArray); // is this the same as array1? 
     takesArgs(anArray, anArray); 
    } 

    public static void takesArgs(Object... stuff) { 
     System.out.println("The array was " + stuff); 
    } 
} 

Il risultato dell'esecuzione (i numeri esatta varia:

object1 = [email protected] 
array1 = [Ljava.lang.Object;@19821f 
The array was [Ljava.lang.Object;@addbf1 
The array was [Ljava.lang.Object;@42e816 
The array was [Ljava.lang.Object;@19821f 
The array was [Ljava.lang.Object;@9304b1 

Quindi la risposta è che in casi ambigui, si tratta di quello che avete passato come la matrice invece di creare una nuova matrice per avvolgerla. Questo ha senso in quanto potresti sempre racchiuderlo in una matrice se desideri l'altra interpretazione.

Problemi correlati