Pourquoi est nul interdit pour DateTime en C #?
-
22-08-2019 - |
Question
Pourquoi est-il pas le droit d'affecter null à un DateTime en C #? Comment cela at-il été mis en œuvre? Et cette fonction peut être utilisée pour faire vos propres classes non annulable?
Exemple:
string stringTest = null; // Okay
DateTime dateTimeTest = null; // Compile error
Je sais que je peux utiliser
La solution DateTime?
en C # 2.0 pour permettre nul à attribuer à dateTimeTest et que je pouvais utiliser
DateTime
est une valeur de type (struct
), là où il en tant que chaîne de caractères est un type de référence (class
etc.). Telle est la principale différence. Une référence peut toujours être nulle; une valeur ne peut pas (à moins qu'il utilise Nullable<T>
- à savoir DateTime?
) (. esp à 1,1)., bien qu'il puisse être zero'd (DateTime.MinValue
), qui est souvent interprété comme la même chose que null
Autres conseils
DateTime est une struct et non une classe. Faites un « aller à la définition » ou regarder dans le navigateur d'objets pour voir.
HTH!
La distinction importante entre les types de types de valeur et référence est que les types de valeur ont ces « sémantique de valeur ». Un DateTime, Int32 et tous les autres types de valeur ont pas d'identité, un Int32 « 42 » est essentiellement impossible à distinguer de toute autre Int32 avec la même valeur.
Tous les types de valeurs « objets » existent soit sur pile ou en tant que partie d'un objet de type de référence. Un cas particulier est lorsque vous lancez une instance de type valeur à un objet ou une interface - ce qu'on appelle « la boxe », et il crée simplement un objet de type de référence factice qui ne contient que la valeur qui peut être extraite en retour ( « unboxed ») .
Types de référence, d'autre part, ont une identité. un « new Object () » ne correspond pas tout autre « new Object () », parce qu'ils sont des instances distinctes sur le tas GC. Certains types référence fournissent méthode Equals et les opérateurs surchargées afin qu'ils se comportent plus de valeur comme, par exemple. une chaîne « abc » est égal à autre chaîne « abc », même si elles sont en fait deux objets différents.
Alors, quand vous avez une référence, il peut soit contenir l'adresse d'un objet valide, ou il peut être nulle. Lorsque des objets de type valeur sont zéro, ils sont tout simplement nul. Par exemple. un nombre entier égal à zéro, un flotteur zéro, FALSE, ou DateTime.MinValue. Si vous avez besoin de faire la distinction entre « zéro » et « valeur manquante / null », vous devez utiliser un drapeau booléen, ou, mieux encore, utilisez la Nullable
DateTime est un type de valeur, même comme un int. Seuls les types de référence (comme chaîne ou MyCustomObject) peuvent être nuls. Les types de référence stockent vraiment « références » à l'emplacement des objets sur le tas.
j'ai trouvé qui explique mieux. et ici article MSDN sur elle
Pour une valeur de type à être nulle, il doit y avoir une certaine valeur, il peut contenir ce qui aurait pas d'autre sens légitime, et que le système saura en quelque sorte doit être considérée comme « nulle » . Certains types de valeur pourraient répondre au premier critère sans nécessiter de stockage supplémentaire. Si .net avait été conçu à partir du sol avec le concept de valeurs nullables à l'esprit, il aurait pu Object include a virtual
IsLogicalNullproperty, and a non-virtual
IsNullwhich would return
trueif
thisis null and, otherwise invoke its
IsLogicalNullproperty and return the result. If .net had done this, it would have avoided the need for the quirky boxing behavior and
structconstraint of
Nullable(an empty
Nullablecould be boxed as an empty
Nullable, and still be recognized as
null`).
Au moment où il a été décidé de fournir un soutien pour les types de valeur nullables dans .NET Framework 2.0, cependant, beaucoup de code a été écrit qui suppose que les valeurs par défaut pour des choses comme Guid
et DateTime
ne seraient pas considérés comme null
. Comme une grande partie de la valeur dans les types nullables se trouve à leur valeur par défaut prévisible (à savoir null
), ayant des types qui avaient une valeur null
, mais par défaut à la autre chose, aurait ajouté plus de confusion que de valeur.
string est une classe alors que DateTime est une structure. C'est pourquoi vous ne pouvez pas le mettre à null