Qual è la differenza tra compare () e compareTo ()?

Qual è la differenza tra i metodi di compare() e compareTo() Java? Quei metodi danno la stessa risposta?

Da JavaNotes :

  • a.compareTo(b) :
    Interfaccia comparabile: confronta i valori e restituisce un int che indica se i valori sono inferiori, uguali o maggiori di.
    Se gli oggetti di class hanno un ordine naturale , implementare l’interfaccia Comparable e definire questo metodo. Tutte le classi Java che dispongono di uno strumento di ordinamento naturale Comparable – Esempio: String , classi wrapper , BigInteger

  • compare(a, b) :
    Interfaccia comparatore: confronta i valori di due oggetti. Questo è implementato come parte dell’interfaccia Comparator e l’ uso tipico è definire una o più classi di utilità di piccole dimensioni che lo implementano, passare a metodi come sort() o per l’uso ordinando strutture di dati come TreeMap e TreeSet . Potresti voler creare un object Comparator per quanto segue:

    • Confronti multipli . Fornire diversi modi per ordinare qualcosa. Ad esempio, potresti voler ordinare una class Person per nome, ID, età, altezza, … Definiresti un Comparatore per ognuno di questi per passare al metodo sort() .
    • Classe di sistema Fornire metodi di confronto per le classi su cui non si ha alcun controllo. Ad esempio, è ansible definire un comparatore per stringhe che li confronta per lunghezza.
    • Schema di strategia Per implementare un modello di strategia, che è una situazione in cui si desidera rappresentare un algoritmo come object che è ansible passare come parametro, salvare in una struttura dati, ecc.

Se i tuoi oggetti di class hanno un ordinamento naturale, potresti non aver bisogno di confrontare ().


Riepilogo da http://www.digizol.com/2008/07/java-sorting-comparator-vs-comparable.html

paragonabile
Un object comparabile è in grado di confrontarsi con un altro object.

comparatore
Un object comparatore è in grado di confrontare due oggetti diversi. La class non sta confrontando le sue istanze, ma alcune istanze di altre classi.


Usa contesti del caso:

Interfaccia comparabile

Il metodo equals e gli operatori == e != Test per l’uguaglianza / disuguaglianza, ma non forniscono un modo per verificare i valori relativi .
Alcune classi (ad es. String e altre classi con un ordinamento naturale) implementano l’interfaccia Comparable , che definisce un metodo compareTo() .
Dovrai implementare Comparable nella tua class se vuoi usarlo con i metodi Collections.sort() o Arrays.sort() .

Definizione di un object comparatore

Puoi creare comparatori per ordinare qualsiasi modo arbitrario per qualsiasi class .
Ad esempio, la class String definisce il comparatore CASE_INSENSITIVE_ORDER .


La differenza tra i due approcci può essere collegata alla nozione di:
Collezione ordinata :

Quando viene ordinata una raccolta, significa che è ansible eseguire l’iterazione nella raccolta in un ordine specifico (non casuale) (un Hashtable non è ordinato).

Una collezione con un ordine naturale non è solo ordinata, ma ordinata . Definire un ordine naturale può essere difficile! (come nell’ordine naturale delle corde ).


Un’altra differenza, sottolineata da HaveAGuess nei commenti :

  • Comparable è nell’implementazione e non visibile dall’interfaccia, quindi quando si ordina non si sa veramente cosa accadrà.
  • Comparator ti dà la sicurezza che l’ordine sarà ben definito.

Analogie:
Entrambi sono modi personalizzati per confrontare due oggetti.
Entrambi restituiscono un int descrive la relazione tra due oggetti.

Differenze: il metodo compare() è un metodo che è obbligatorio implementare se si implementa l’interfaccia di Comparator . Permette di passare due oggetti nel metodo e restituisce un int descrive la loro relazione.

 Comparator comp = new MyComparator(); int result = comp.compare(object1, object2); 

Il metodo compareTo() è un metodo che sei obbligato ad implementare se implementi l’interfaccia Comparable . Consente a un object di essere confrontato con oggetti di tipo simile.

 String s = "hi"; int result = s.compareTo("bye"); 

Sommario:
Fondamentalmente sono due modi diversi per confrontare le cose.

compareTo() è dall’interfaccia Comparable .

compare() è dall’interfaccia di Comparator .

Entrambi i metodi fanno la stessa cosa, ma ogni interfaccia viene utilizzata in un contesto leggermente diverso.

L’interfaccia Comparable viene utilizzata per imporre un ordinamento naturale sugli oggetti della class di implementazione. Il metodo compareTo() è chiamato il metodo di confronto naturale. L’interfaccia di Comparatore viene utilizzata per imporre un ordinamento totale sugli oggetti della class di implementazione. Per ulteriori informazioni, vedere i collegamenti per quando esattamente utilizzare ciascuna interfaccia.

I metodi non devono dare le stesse risposte. Dipende da quali oggetti / classi li chiami.

Se stai implementando le tue classi che sai che vuoi confrontare in qualche momento, potresti averli implementare l’interfaccia Comparable e implementare il metodo compareTo () di conseguenza.

Se stai utilizzando alcune classi da un’API che non implementa l’interfaccia Comparable, ma vuoi comunque confrontarle. Vale a dire per l’ordinamento. Puoi creare la tua class che implementa l’interfaccia di Comparator e nel suo metodo di confronto () implementerai la logica.

L’ interfaccia comparabile contiene un metodo chiamato compareTo(obj) che accetta un solo argomento e si confronta con un’altra istanza o oggetti della stessa class.

L’ interfaccia di Comparator contiene un metodo chiamato compare(obj1,obj2) che accetta due argomenti e confronta il valore di due oggetti della stessa class o di classi diverse.

 compareTo(T object) 

viene dall’interfaccia java.lang.Comparable, implementata per confrontare questo object con un altro per fornire un valore int negativo per questo object inferiore a, 0 per uguale, o valore positivo per maggiore dell’altra. Questo è il metodo di confronto più conveniente, ma deve essere implementato in ogni class che si desidera confrontare.

 compare(T obj1, T obj2) 

viene dall’interfaccia java.util.Comparator, implementata in una class separata che confronta gli oggetti di un’altra class per fornire un valore int negativo per il primo object inferiore a, 0 per uguale, o valore positivo per maggiore del secondo object. È necessario quando non è ansible realizzare un programma di class compareTo () perché non è modificabile. Viene anche utilizzato quando si desiderano diversi modi per confrontare gli oggetti, non solo uno (ad esempio per nome o per età).

Usando Comparator, possiamo avere n numero di logiche di confronto scritte per una class .

Per esempio

Per una class di auto

Possiamo avere una class di Comparatori da confrontare in base al numero di modello di auto. Possiamo anche avere una class di Comparatori da confrontare in base all’anno del modello di auto.

Classe di auto

 public class Car { int modelNo; int modelYear; public int getModelNo() { return modelNo; } public void setModelNo(int modelNo) { this.modelNo = modelNo; } public int getModelYear() { return modelYear; } public void setModelYear(int modelYear) { this.modelYear = modelYear; } } 

Comparatore n. 1 basato sul modello n

 public class CarModelNoCompartor implements Comparator{ public int compare(Car o1, Car o2) { return o1.getModelNo() - o2.getModelNo(); } } 

Comparatore n. 2 basato sull’anno del modello

 public class CarModelYearComparator implements Comparator { public int compare(Car o1, Car o2) { return o1.getModelYear() - o2.getModelYear(); } } 

Ma questo non è ansible con l’interfaccia Comparable .

In caso di interfaccia comparabile, possiamo avere una sola logica nel metodo compareTo () .

La relazione dell’object che ha questo metodo e i suoi collaboratori è diversa.

compareTo() è un metodo dell’interfaccia Comparable , quindi è usato per confrontare QUESTA istanza con un’altra.

compare() è un metodo dell’interfaccia Comparator , quindi è usato per confrontare due diverse istanze di un’altra class l’una con l’altra.

Se lo si desidera, l’implementazione di Comparable significa che le istanze della class possono essere facilmente confrontate.
Implementare Comparator significa che le istanze sono adatte per confrontare oggetti diversi (di altre classi).

compareTo() viene chiamato su un object, per confrontarlo con un altro object. compare() viene chiamato su alcuni oggetti per confrontare altri due oggetti.

La differenza è dove viene definita la logica che fa il confronto effettivo.

Quando si desidera ordinare un elenco che include l’object Foo, la class Foo deve implementare l’interfaccia Comparable, poiché il metodo sort dell’elenco sta utilizzando questo metodo.

Quando si desidera scrivere una class Util che confronta due altre classi, è ansible implementare la class Comparator.

La principale differenza sta nell’uso delle interfacce:

Comparabile (che ha compareTo ()) richiede che gli oggetti siano confrontati (per usare una TreeMap, o per ordinare una lista) per implementare quell’interfaccia. Ma cosa succede se la class non implementa Comparable e non puoi cambiarla perché fa parte di una libreria di terze parti? Quindi devi implementare un comparatore, che è un po ‘meno comodo da usare.

Tavolo dei dipendenti
Nome, DoB, Stipendio
Tomas, 2/10/1982, 300
Daniel, 3/11/1990, 400
Kwame, 2/10/1998, 520

L’interfaccia Comparable ti consente di ordinare un elenco di oggetti, ad esempio Dipendenti con riferimento a un campo primario; ad esempio, puoi ordinare per nome o per stipendio con il metodo CompareTo ()

 emp1.getName().compareTo(emp2.getName()) 

Un’interfaccia più flessibile per tali requisiti è fornita dall’interfaccia di Comparator , il cui unico metodo è compare ()

 public interface Comparator { int compare(Employee obj1, Employee obj2); } 

Codice d’esempio

 public class NameComparator implements Comparator { public int compare(Employee e1, Employee e2) { // some conditions here return e1.getName().compareTo(e2.getName()); // returns 1 since (T)omas > (D)an return e1.getSalary().compareTo(e2.getSalary()); // returns -1 since 400 > 300 } 

}

Un altro punto:

  • compareTo() è dall’interfaccia Comparable e compare() è dall’interfaccia Comparator .
  • Comparable viene utilizzato per definire un ordinamento predefinito per gli oggetti all’interno di una class mentre Comparator viene utilizzato per definire un ordine personalizzato da passare a un metodo.

C’è anche un aspetto tecnico da sottolineare. Supponiamo di aver bisogno della parametrizzazione del comportamento di confronto da una class client, e ti stai chiedendo se usare Comparable o Comparator per un metodo come questo:

 class Pokemon { int healthPoints; int attackDamage; public void battle (Comparable comparable, Pokemon opponent) { if (comparable.compareTo(opponent) > 0) { //comparable needs to, but cannot, access this.healthPoints for example System.out.println("battle won"); } else { System.out.println("battle lost"); } } } 

comparable sarebbe un lambda o un object, e non c’è modo per comparable di accedere ai campi di this Pokemon. (In un lambda, this riferisce all’istanza di class esterna nello scope di lambda, come definito nel testo del programma.) Quindi questo non vola , e dobbiamo usare un Comparator con due argomenti.

 Important Answar String name; int roll; public int compare(Object obj1,Object obj2) { // For Comparator interface return obj1.compareTo(obj1); } public int compareTo(Object obj1) { // For Comparable Interface return obj1.compareTo(obj); } 

Qui in return obj1.compareTo(obj1) o return obj1.compareTo(obj) statement return obj1.compareTo(obj) solo Object; primitivo non è permesso. Per esempio

 name.compareTo(obj1.getName()) // Correct Statement. 

Ma

 roll.compareTo(obj1.getRoll()) // Wrong Statement Compile Time Error Because roll // is not an Object Type, it is primitive type. 

il nome è Oggetto String, quindi ha funzionato. Se si desidera ordinare il numero di rotoli di studenti piuttosto che usare il codice sottostante.

 public int compareTo(Object obj1) { // For Comparable Interface Student s = (Student) obj1; return rollno - s.getRollno(); } 

o

 public int compare(Object obj1,Object obj2) { // For Comparator interface Student s1 = (Student) obj1; Student s2 = (Student) obj2; return s1.getRollno() - s2.getRollno(); }