2014-09-16 7 views
6

Come si può avere un metodo con due parametri, con entrambi i parametri aventi lo stesso tipo di calcestruzzo?Forzare due parametri di un metodo generico per avere lo stesso tipo di calcestruzzo

Ad esempio,

boolean equals(Object a, Object b) 

consente una a di qualunque tipo e b di qualsiasi tipo.

Voglio forzare tale che a e abbiano lo stesso tipo di calcestruzzo. Ho provato

<T> boolean equals(T a, T b) 

e inserendo un Date e un String a tale metodo, in attesa di un errore di compilazione, ma ottengo nessun errore, dal momento che T risolverà a ? extends Serializable & Comparable, dal momento che entrambi Date e String implementa Serializable e Comparable.

+1

Perché mai vorresti farlo? – AJMansfield

risposta

7

Non è possibile, in pratica. Non c'è modo di farlo. Anche se si potrebbe fare per una semplice chiamata per vietare argomenti di tipo diverso, si potrebbe sempre essere aggirato utilizzando un cast:

equals((Object) date, (Object) string) 

Se siete interessati al tempo di esecuzione tipi di argomenti, puoi solo verificarlo al momento dell'esecuzione. Non c'è modo che il compilatore sappia se un argomento di tipo Date ha un valore che è un riferimento a precisamente a java.util.Date o qualche sottoclasse.

+0

Grazie per la risposta velocissima. – yuku

1

La cosa è la firma del metodo diventa

<? extends Object> boolean equals(? extends Object a, ? extends Object b) 

, che non ti dà tutte le opzioni. Anche se si chiama

equals(new Date(), "hello world"); 

il compilatore non ha nemmeno bisogno di rompere un sudore e determinare il più basso antenato comune per i tipi di parametri.

Modifica

Fatto interessante. Sapevo che quello che ho scritto sopra era vero, ma sembrava ancora un po 'strano. Così ho provato

<T> boolean equals(T a, T b) { 
    return true; 
} 

<T,E> boolean equals(T a, E b) { 
    return true; 
} 

A cui il compilatore ha urlato. La ragione è che il compilatore effettivamente non fa differenza e solo riscrive entrambi i metodi come

boolean equals(? extends Object a, ? extends Object b) 

che, dopo la cancellazione di tipo diventa

boolean equals(Object a, Object b) 

che è la stessa firma. Effettivamente, se tengo il tuo metodo equals(T,T) e aggiungo un altro metodo con la firma equals(Object, Object), il compilatore continua a dire che ho lo stesso metodo dichiarato altrove.

farla breve, il metodo di equals(T,T) è lo stesso equals(Object, Object) a causa della cancellazione di tipo e quindi non è possibile forzare lo stesso tipo di parametro, almeno al momento della compilazione, a meno che non di implementare specificamente equals metodi per ogni .