Controllare la mancanza di collezioni con (in) uguaglianze: qual è la migliore pratica?

0

Da molto tempo ormai avevo l'abitudine di controllare se una collezione (array, dizionario, qualunque cosa) non è vuota con una non uguaglianza. In questo modo:

if ( MyArray.Length < 1 )
{
    // Do something if the array is empty
}

A volte lo faccio anche per le stringhe e altri tipi di raccolte. In pratica, dovrebbe essere uguale a

if ( MyArray.Length == 0 )
{
    // Do something if the array is empty
}

Perché la lunghezza della raccolta non dovrebbe mai essere inferiore a 0 comunque, giusto? Quindi ho sempre pensato: che diamine, includerò la disuguaglianza e sarei protetto da una doppia sicurezza anche nel caso in cui il cielo cada.

Ma oggi mi è sembrato che la seconda versione fosse più leggibile della prima. Esprime più chiaramente che il caso che sto cercando è l'array vuoto, che non è immediatamente evidente dalla prima versione. Quindi forse dovrei usarlo invece? Dal momento che, sai, se una lunghezza di raccolta è inferiore a 0, allora sono fottuto comunque.

Quale versione usi e quale suggeriresti ad altri di usare (e perché)?

Chiarificazione: era inteso come una domanda sulle raccolte semplici, dove ottenere .Length è O (1) o comunque poco costoso. Se .Length è un'operazione non banale (come richiedere l'iterazione attraverso un elenco collegato o contattare il DB), allora questo è l'approccio sbagliato del tutto.

La domanda era circa x < 1 vs x == 0 dove x è un numero intero non negativo (sebbene non possa essere digitato come tale).

    
posta Vilx- 25.05.2012 - 13:00
fonte

4 risposte

8

Alcune raccolte vuote hanno una lunghezza pari a zero.

Alcune raccolte con una lunghezza negativa sono un'altra cosa.

Usa il secondo o implementa un metodo come IsEmpty ().

    
risposta data 25.05.2012 - 13:05
fonte
1

Personalmente, penso che nessuna delle due versioni sia buona, ed entrambe sono un segno di cattiva progettazione dell'API su parte dell'autore di Array .

Ad esempio, in Ruby (non che io proporrei la libreria di base di Ruby come esempio di buona progettazione API) sarebbe

do_something if my_array.empty?

Che per coincidenza è quasi uguale al tuo commento in prosa inglese.

Aiuta anche a rendere il codice più generico, perché il controllo per il vuoto è possibile in O (1) passi per quasi tutte le raccolte, mentre il calcolo della lunghezza può richiedere fino a O (n) (nel caso di un elenco collegato, per esempio) o anche per sempre (nel caso di un flusso pigro infinito).

Pensa

list_of_all_primes.empty?

vs.

list_of_all_primes.length.zero? # Oops.
    
risposta data 25.05.2012 - 14:19
fonte
0

Considerando solo "==" e "<", la domanda, mi sembra, è ciò che stai stai per fare se la lunghezza è negativa? La cosa più intelligente da fare è ignorare la domanda, perché non accadrà. Avendo fallito, la cosa corretta da fare è fermare il programma e far scattare gli allarmi perché qualcosa è davvero sbagliato. Ma nessuno lo farà neanche. Quindi, infine, è necessario considerare la migliore linea d'azione con un valore negativo. Direi che la maggior parte delle volte lo tratta come zero (usando "< 1") è la via più sicura. Ma proverei a psicanalizzare chiunque abbia scritto la collezione e basare la mia decisione finale su questo.

Tieni presente che "< 1" è la rotta più semplice . Se -5 fa non significa che la raccolta è vuota, fa significa che c'è un elemento 4? O significa che c'è un elemento -4 ? Se vuoi essere coerente, se usi "== 0" devi codificare per gestire le lunghezze negative quando la lunghezza non è uguale a zero. Quindi, in generale , voterò per "< 1".

    
risposta data 25.05.2012 - 22:02
fonte
0

Prima verificherei se esiste un metodo chiamato "vuoto", "è vuoto" o simile. Il motivo: il tuo controllo MyArray.Length < 1 determina la lunghezza dell'array, anche se non ti interessa affatto la lunghezza, solo nel fatto che è 0 o meno 0. Per alcuni casi con una lunghezza enorme, determinare la lunghezza potrebbe richiedere molto tempo, mentre rilevare che la lunghezza non è zero è immediata.

Supponiamo di avere una classe stringa, con "lunghezza" che restituisce il numero di punti codice Unicode. Ma internamente la stringa viene archiviata nel formato UTF-8. Se c'è un milione di byte, quindi per determinare la "lunghezza" è necessario esaminare ogni singolo byte. D'altra parte, controllare che la lunghezza non sia zero è banale.

O prendi un elenco collegato. Controllare che abbia più di 0 elementi è banale, ma in realtà il calcolo della lunghezza può richiedere molto tempo.

    
risposta data 22.06.2015 - 12:41
fonte

Leggi altre domande sui tag