L'avviso è uguale a / hashCode nell'annotazione @Data lombok con ereditarietà


103

Ho un'entità che eredita da altri. D'altra parte, sto usando il progetto lombok per ridurre il codice boilerplate, quindi ho inserito l' @Dataannotazione. L'annotazione @Datacon ereditarietà produce l'avviso successivo:

Generazione dell'implementazione di uguale / hashCode ma senza una chiamata alla superclasse, anche se questa classe non estende java.lang.Object. Se è intenzionale, aggiungi @EqualsAndHashCode(callSuper=false)al tuo tipo.

È consigliabile aggiungere annotazioni @EqualsAndHashCode (callSuper = true)o @EqualsAndHashCode (callSuper = false)? Se non è aggiunto, quale è callSuper=falseo callSuper=true?

Risposte:


125

Il valore predefinito è false. Questo è quello che ottieni se non lo specifichi e ignori l'avviso.

Sì, si consiglia di aggiungere @EqualsAndHashCodeun'annotazione sulle @Dataclassi annotate che estendono qualcosa di diverso da Object. Non posso dirti se hai bisogno di trueo false, dipende dalla tua gerarchia di classe, e dovrà essere esaminato caso per caso.

Tuttavia, per un progetto o un pacchetto, puoi configurare in lombok.configper chiamare i super metodi se non è una sottoclasse diretta di Object.

lombok.equalsAndHashCode.callSuper = call

Vedere la documentazione del sistema di configurazione su come funziona e la @EqualsEndHashCodedocumentazione per le chiavi di configurazione supportate.

Divulgazione: sono uno sviluppatore lombok.


Ha funzionato per me. Ma tieni presente che affinché il plug-in delombok raccolga questo file di configurazione, dovrebbe essere posizionato nella directory root dei sorgenti java, non nella directory delle risorse, cioè in src / main / java e non in src / main / resources
user577736

1
@Roel mi chiedo perché l'impostazione predefinita è falsa. Mi sarei aspettato il contrario. Inoltre, esiste un modo equivalente per ottenere toString () per chiamare super per impostazione predefinita? Vedo che posso fare "@ToString (callSuper = true)", ma non vedo alcuna impostazione di configurazione di questo tipo. Grazie.
David Siegal

È importante se aggiungo @EqualsAndHashCode (callSuper = true) prima o dopo @Data?
Anna Klein

@AnnaKlein l'ordine non importa
dan carter

47

@EqualsAndHashCode(callSuper=true) dovrebbe risolvere l'avviso.


1
Questa dovrebbe essere la risposta accettata poiché non penso che il suggerimento di Roel dovrebbe essere fatto "lombok.equalsAndHashCode.callSuper = call" invece dovrebbe essere presa una decisione per ogni classe.
Anna Klein

4
@AnnaKlein Non credo. In effetti questa risposta dovrebbe essere un commento, non ci sono nuove informazioni qui, puoi trovarle nella mia domanda. @EqualsAndHashCodeSapevo che risolve l'avvertimento.
Pau

In realtà per la risposta accettata (e la mia risposta di seguito) dovresti scegliere tra "callSuper = true" o "callSuper = false" nell'annotazione.
Adam Wise

27

La principale domanda originale è:

È consigliabile aggiungere l'annotazione @EqualsAndHashCode (callSuper = true) o @EqualsAndHashCode (callSuper = false)?

La risposta accettata è fondamentalmente solo:

...dipende...

Per espandere questo aspetto , la documentazione su @EqualsAndHashCode ha alcune solide indicazioni su cui scegliere. Soprattutto questo, IMHO:

Impostando callSuper su true, puoi includere i metodi equals e hashCode della tua superclasse nei metodi generati. Per hashCode, il risultato di super.hashCode () è incluso nell'algoritmo hash e forequals, il metodo generato restituirà false se l'implementazione super pensa che non sia uguale all'oggetto passato. Tieni presente che non tutte le implementazioni uguali gestiscono correttamente questa situazione. Tuttavia, le implementazioni uguali generate da lombok gestiscono correttamente questa situazione, quindi puoi tranquillamente chiamare la tua superclasse uguale se anch'essa ha un metodo uguale generato da lombok.

Per riassumere questo un po ': scegli' callSuper = true 'se stai ereditando da una superclasse che non ha informazioni sullo stato, o sta usando l'annotazione @Data, o ha implementazioni di uguale / hash che "gestiscono la situazione correttamente" - che interpreto per indicare la restituzione di un hash corretto dei valori di stato.


Penso che questa sia la risposta che spiega bene come scegliere tra callSuper = false e callSuper = true.
recita il

10

Se vuoi confrontare anche i membri della superclasse, usa @EqualsAndHashCode(callSuper=true). Se, tuttavia, desideri confrontare solo i campi nella classe corrente, puoi utilizzare @EqualsAndHashCode(callSuper=false)l' opzione predefinita .

Se usi la funzione di Delombok puoi vedere che la differenza è che quando impostato su truequesta linea viene aggiunto al metodo di uguaglianza generato if (!super.equals(o)) return false;. Se hai membri nella superclasse che dovrebbero essere presi in considerazione quando si confrontano due oggetti, allora deve essere impostato su true per confrontare correttamente.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.