Java: errore .equals () per i set (JGraphT)
Domanda
Non riesco a capire cosa non va qui. Questo test ha esito negativo:
@Test
public void testSimpleCase() {
assertTrue(JGraphtUtilities.graphEquality(ChooseRootTest.generateSimpleCaseGraph(), ChooseRootTest.generateSimpleCaseGraph()));
}
public static <V, E> boolean graphEquality(Graph<V, E> g0, Graph<V, E> g1) {
boolean result = true;
if (g0.edgeSet().equals(g1.edgeSet()) && g0.vertexSet().equals(g1.vertexSet())) {
for (E e : g0.edgeSet()) {
if (g0.getEdgeWeight(e) != g1.getEdgeWeight(e)) {
result = false;
}
}
}
else {
return false; //for the above test, this is what is returned
}
return result;
}
Il debugger mostra che il metodo decide che i due set di vertici e set di bordi non sono uguali, quindi restituisce false. Come è possibile?
Nota a margine: sto cercando di scrivere un controllo di uguaglianza per i grafici JGraphT. Come è possibile che ciò non sia già stato fatto?
AGGIORNAMENTO: Penso che DefaultWeightedEdge non abbia la precedenza sugli uguali, quindi non funzionerebbe. Ho fatto un modo diverso di verificare l'esistenza dei bordi tra tutti i vertici necessari e ora sembra funzionare.
Soluzione
Secondo JavaDoc DefaultWeightedEdge
non ha implementato equals ()
e hashCode ()
e quindi utilizza i metodi definiti in java.lang.Object
. Ciò significa che due oggetti DefaultWeightedEdge
a
e b
con gli stessi valori non restituiranno true da
a.equals (b)
. Ciò restituirebbe true
se a
e b
si riferissero effettivamente allo stesso oggetto.
È necessario utilizzare una classe di implementazione edge che implementa .equals ()
e hashCode ()
per ottenere risultati utili qui.
Altri suggerimenti
Non ho familiarità con JGraphT, ma ci sono due problemi a cui posso pensare.
In primo luogo, cosa significa che due serie di bordi sono equivalenti? Cosa rende equivalenti due bordi? Se creo un grafico e creo un grafico identico separatamente, entrambi potrebbero avere la stessa struttura. Ma se il confronto dei bordi di due bordi corrispondenti utilizza le identità del nodo, i due bordi non sarebbero "uguali".
Secondo, l'ho notato in JavaDocs:
" L'implementazione del grafico può mantenere un particolare ordinamento di set (ad es. tramite LinkedHashSet) per l'iterazione deterministica, ma ciò non è necessario. È responsabilità dei chiamanti che fanno affidamento su questo comportamento utilizzare solo implementazioni grafiche che lo supportano. & Quot;
Proverei (almeno per la sanità mentale) ad assicurarmi che i due insiemi si contengano, poiché è possibile che uguale a non sia implementato correttamente (ad esempio, potrebbe prendere in considerazione l'ordine).