Domanda

Sono un po 'confuso riguardo a valori e variabili null in .NET. (VB preferito)

Esiste un modo per controllare " nullness " di QUALSIASI variabile data indipendentemente dal fatto che fosse un oggetto o un tipo di valore? O il mio controllo null deve sempre prevedere se sta controllando un tipo di valore (ad esempio System.Integer) o un oggetto?

Suppongo che ciò che sto cercando sia una funzione che controlli tutti i possibili tipi di nullità. Cioè, qualsiasi tipo di variabile che

a) non è mai stato assegnato un valore da quando dichiarato

b) è stato assegnato un valore nullo da un oggetto dati (proveniente da un database)

c) sono stati impostati uguali a un altro valore variabile che era null

d) sono stati impostati su una variabile di sessione / applicazione ASP.NET che non è mai stata impostata o scaduta.

Esiste una best practice generale quando si tratta di gestire scenari null in .NET?

AGGIORNAMENTO: Quando parlo di un tipo di valore che è " null " ;, ciò che intendo veramente è un tipo di valore che non è mai stato impostato o che a un certo punto impostato uguale o cast da un oggetto null.

È stato utile?

Soluzione

I tipi di valori normali (booleani, ints, long, float, double, enum e struct) non sono nullable.

Il valore predefinito per tutti i tipi di valore è 0.

Il CLR non ti consentirà di accedere alle variabili se non sono state impostate. Potresti pensare che non sia sempre così, ma a volte il CLR interviene e li inizializza per te. A livello di metodo è necessario inizializzare esplicitamente tutte le variabili prima che vengano utilizzate.

Inoltre, come altri sottolineano, poiché .net 2.0 esiste un nuovo tipo generico chiamato Nullable<T>. Ci sono alcune scorciatoie del compilatore in C # come int? significa Nullable<int>, doppio? significa Nullable<double> ecc.

Puoi avvolgere x.HasValue() solo su tipi di valori non annullabili, il che va bene poiché i riferimenti hanno già la possibilità di essere nulli.

int? x = null;

Per un int ?, mentre puoi provare contro null, a volte è più bello chiamare <=>.

In C # c'è anche il operatore a coalescenza nullable ?? quando si desidera assegnare un nullable a un tipo di valore non nullable. Ma se non si dispone dell'operatore, è possibile chiamare GetValueOrDefault ().

int y = x ?? 2; // y becomes 2 if x is null.
int z = x.GetValueOrDefault(2); // same as y

Altri suggerimenti

I tipi di valore non possono essere nulli. Viola il significato di essere un tipo di valore. Puoi racchiudere Tipi di valore come Nullable (Of T) che ti offre una grande serie di metodi e verifica che Nothing do work. Ma hai un sacco di spese generali con quel wrapper. Forse puoi chiarire cosa stai cercando di fare?

Per completezza la sintassi VB per i wrapper Nullable è:

Dim i as Nullable(Of Integer) = Nothing '.NET 2.0/3.0'
Dim j as Integer? = Nothing '.NET 3.5'

EDIT: i tipi di valore sono sempre preinizializzati su un valore predefinito, 0 per i numeri, falso per i booleani, ecc.

È questo ciò che cerchi?

if IsNothing(foo) OrElse IsDbNull(foo) Then
    ' Do Something Because foo Is Either Nothing or DBNull.Value
End If

In verità non sono sicuro del motivo per cui vorresti questa struttura. L'unica volta che controllo DBNULL.Value è quando sto usando valori che provengono da un database e prima di assegnare tale valore da una classe DATA Namespace ad un'altra classe [ad es. dim b as string = dataReader (0)].

In genere, se si è preoccupati che un oggetto non sia stato istanziato o che sia necessario ri-istanziarlo, sarà sufficiente solo un controllo IsNothing.

In .Net che sono solo due tipi di null di cui sono a conoscenza, null (niente in VB) e DbNull. Se si utilizza System.Nullable, è possibile utilizzare la stessa sintassi di controllo null che si farebbe con un oggetto. Se il tuo oggetto nullable è inscatolato, il CLR .Net 2.0 è abbastanza intelligente da capire il modo giusto di gestirlo.

L'unico caso in cui mi sono imbattuto in entrambi i tipi è nel livello dati di un'applicazione in cui potrei accedere direttamente ai dati del database. Ad esempio, ho incontrato DbNull in una DataTable. Per verificare entrambi questi tipi nulli in questa situration, puoi scrivere un metodo di estensione come (scusa, in C #):

static public bool IsNull(this object obj)
{
    return obj != null && obj != DbNull.Value;
}

...

if(dataTable[0]["MyColumn"].IsNull())
{
  //do something
}

Le variabili del tipo di valore non possono contenere null, poiché ciò significa null, null significa che i riferimenti non puntano da nessuna parte. Non lo so su VB.net ma su c # puoi racchiudere i tipi di valore in modo che sia nullable usando & Quot;? & Quot ;, come:

int? a = null;

Finché stai sviluppando con Option Strict On, (a) non dovrebbe essere un problema. Il compilatore ti urlerà. Se sei preoccupato di controllare i parametri, usa

Public Sub MySub(ByVal param1 as MyObject, ByVal param2 as Integer)
    if param1 is nothing then
         Throw New ArgumentException("param1 cannot be null!")
    end if
    'param2 cannot be null
End Sub

Per (b), il livello di interazione del database dovrebbe gestirlo. Se stai usando LINQ, ci sono modi per gestirlo. Se stai utilizzando set di dati digitati, c'è una proprietà .IsMyVariableNull sulla riga che viene generata automaticamente.

Per (c), non devi preoccuparti dei tipi di valore, ma i tipi di riferimento possono essere controllati con un semplice Is Nothing (o IsNot Nothing).

Per (d), è possibile applicare la stessa logica dopo la lettura. Prova la variabile di ricezione con Nothing.

Per la maggior parte, un semplice controllo di Is Nothing ti farà passare. Il tuo livello di interazione con il database ti aiuterà a gestire il caso più appiccicoso di valori null nei tuoi dati, ma spetta a te gestirli in modo appropriato.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top