2010-11-15 10 views
41

sto popolando un array con le istanze di una classe:Come implementare l'interfaccia IComparable?

BankAccount[] a; 
. . . 

a = new BankAccount[] 
{ 
    new BankAccount("George Smith", 500m), 
    new BankAccount("Sid Zimmerman", 300m) 
}; 

Una volta io popolo questa matrice, vorrei ordinare che di quantità di equilibrio. Per farlo, vorrei essere in grado di verificare se ogni elemento è ordinabile utilizzando IComparable.
Ho bisogno di fare questo usando le interfacce. Finora ho il seguente codice:

public interface IComparable 
{ 
    decimal CompareTo(BankAccount obj); 
} 

Ma non sono sicuro se questa è la soluzione giusta. Qualche consiglio?

risposta

79

Non è necessario definire ICcomparable da soli. È già definito.

Piuttosto, è necessario attuare IComparable sulla classe BankAccount.

Dove si è definito il class BankAccount, assicurarsi che implementa l'interfaccia IComparable

Quindi scrivere BankAccout.CompareTo per confrontare i valori dello stato dei due oggetti.


Modifica

public class BankAccount : IComparable<BankAccount> 
{ 
    [...] 

    public int CompareTo(BankAccount that) 
    { 
     if (this.Balance > that.Balance) return -1; 
     if (this.Balance == that.Balance) return 0; 
     return 1; 
    } 
} 

Edit 2 per mostrare buona risposta di Jeffrey L Whitledge:

public class BankAccount : IComparable<BankAccount> 
{ 
    [...] 

    public int CompareTo(BankAccount that) 
    { 
     return this.Balance.CompareTo(that.Balance); 
    } 
} 
+0

mi dispiace u può darmi un esempio di come vorrei implementarlo –

+26

'Mi piace tornare this.Balance. CompareTo (that.Balance); ' –

+0

@jeff è solo una sintassi sbagliata –

4

C'è già IComparable<T>, ma è consigliabile supportare idealmente sia IComparable<T> sia IComparable. L'utilizzo del built-in Comparer<T>.Default è generalmente un'opzione più semplice. Array.Sort, ad esempio, accetterà tale confronto.

14

IComparable esiste già in .NET con questa definizione di CompareTo

int CompareTo(Object obj) 

Non si deve creare l'interfaccia, si suppone che la si debba implementare.

public class BankAccount : IComparable { 

    int CompareTo(Object obj) { 
      // return Less than zero if this object 
      // is less than the object specified by the CompareTo method. 

      // return Zero if this object is equal to the object 
      // specified by the CompareTo method. 

      // return Greater than zero if this object is greater than 
      // the object specified by the CompareTo method. 
    } 
} 
+0

mi dispiace puoi darmi un esempio di come vorrei implementarlo –

9

Un'alternativa è quella di utilizzare LINQ e saltare attuazione IComparable del tutto:

BankAccount[] sorted = a.OrderBy(ba => ba.Balance).ToArray(); 
12

Vuoi per distruttivo ordinare l'array? Cioè, vuoi veramente cambiare l'ordine degli elementi nell'array? O vuoi solo un elenco degli articoli in un ordine particolare, senza distruggere l'ordine originale?

Suggerirei che è quasi sempre meglio fare quest'ultimo. Prendi in considerazione l'utilizzo di LINQ per un ordinamento non distruttivo. (E considera l'utilizzo di un nome di variabile più significativo di "a".)

BankAccount[] bankAccounts = { whatever }; 
var sortedByBalance = from bankAccount in bankAccounts 
         orderby bankAccount.Balance 
         select bankAccount; 
Display(sortedByBalance); 
+0

Voglio distruggerlo implementando icompare –

+7

@Lippert: Mentre questa è una risposta molto valida, sembra dalla discussione che l'OP capisca a malapena cosa significa implementare un'interfaccia Probabilmente non è ancora pronta per il livello di domande che stai ponendo. – abelenky

+0

Ciao Eric, qual è la migliore pratica per trattare con 'null' quando si implementa' IComparable 'e la sottoclasse di' Comparer 'assumendo che' T' sia un tipo di riferimento? Dipende dal caso dell'utente o normalmente è meglio lanciare un'eccezione poiché la logica di confronto reale viene spesso inoltrata ad alcune proprietà su 'T'. – stt106

1

Se avete solo bisogno di ordinare questi BankAccounts, utilizzare LINQ come seguire

BankAccount[] a = new BankAccount[] 
{ 
    new BankAccount("George Smith", 500m), 
    new BankAccount("Sid Zimmerman", 300m) 
}; 

a = a.OrderBy(bank => bank.Balance).ToArray();