Ritenere:
Linguaggio,
Struttura,
Contesto.
1. Lingua
L'uso di ∞ può essere una soluzione per un massimo.
JavaScript, ad esempio, ha un infinito. C # non¹.
Ada, ad esempio, ha intervalli. C # no.
In C # c'è int.MaxValue, ma non puoi usarlo nel tuo caso. int.MaxValueè il numero intero massimo, 2.147.483.647. Se nel tuo codice hai un valore massimo di qualcosa, come una pressione massima accettata prima che qualcosa esploda, usare 2.147.483.647 non ha senso.
2. Quadro
.NET Framework è piuttosto incoerente su questo punto e il suo utilizzo di valori magici può essere criticato.
Ad esempio, "Hello".IndexOf("Z")restituisce un valore magico -1. E ' forse rende più facile (lo fa?) Per manipolare il risultato:
int position = "Hello".IndexOf("Z");
if (position > 0)
{
DoSomething(position);
}
anziché utilizzare una struttura personalizzata:
SearchOccurrence occurrence = "Hello".IndexOf("Z");
if (occurrence.IsFound)
{
DoSomething(occurrence.StartOffset);
}
ma non è affatto intuitivo. Perché -1e no -123? Un principiante può anche erroneamente pensare che 0significhi anche "Non trovato" o semplicemente digitare male (position >= 0).
3. Contesto
Se il tuo codice è correlato a timeout nei socket di rete, utilizzare qualcosa che è stato usato da decenni per motivi di coerenza non è una cattiva idea . Soprattutto, 0per un timeout è molto chiaro: è un valore che non può essere zero. L'uso di una classe personalizzata in questo caso può rendere le cose più difficili da capire:
class Timeout
{
// A value indicating whether there is a timeout.
public bool IsTimeoutEnabled { get; set; }
// The duration of the timeout, in milliseconds.
public int Duration { get; set; }
}
- Posso impostare
Durationsu 0 se IsTimeoutEnabledè vero?
- Se
IsTimeoutEnabledè falso, cosa succede se imposto Durationsu 100?
Questo può portare a più errori. Immagina il seguente codice:
this.currentOperation.Timeout = new Timeout
{
// Set the timeout to 200 ms.; we don't want this operation to be longer than that.
Duration = 200,
};
this.currentOperation.Run();
L'operazione dura dieci secondi. Riesci a vedere cosa c'è che non va in questo codice, senza leggere la documentazione della Timeoutclasse?
Conclusione
nullesprime bene l'idea che il valore non sia qui. Non viene fornito. Non disponibile. Non è né un numero, né una stringa zero / vuota o qualsiasi altra cosa. Non utilizzarlo per valori massimi o minimi.
int.MaxValueè fortemente correlato alla lingua stessa. Non utilizzare int.MaxValueper un limite di velocità massima della Vehicleclasse o una velocità massima accettabile per un aeromobile, ecc.
Evita valori magici come -1nel tuo codice. Sono fuorvianti e portano a errori nel codice.
Crea la tua classe che sarebbe più semplice, con i valori minimo / massimo specificati. Ad esempio VehicleSpeedpuò avere VehicleSpeed.MaxValue.
Non seguire alcuna linea guida precedente e utilizzare valori magici se si tratta di una convenzione generale per decenni in un campo molto specifico, utilizzato dalla maggior parte delle persone che scrivono codice in questo campo.
Non dimenticare di mescolare gli approcci. Per esempio:
class DnsQuery
{
public const int NoTimeout = 0;
public int Timeout { get; set; }
}
this.query.Timeout = 0; // For people who are familiar with timeouts set to zero.
// or
this.query.Timeout = DnsQuery.NoTimeout; // For other people.
¹ È possibile creare il proprio tipo che include l'infinito. Qui, sto parlando intsolo di tipo nativo .