Je voudrais empêcher tout traitement supplémentaire sur un objet s'il est nul.
Dans le code suivant, je vérifie si l'objet est nul soit:
if (!data.Equals(null))
et
if (data != null)
Cependant, je reçois un NullReferenceException
at dataList.Add(data)
. Si l'objet était nul, il n'aurait même jamais dû entrer dans la if
déclaration-!
Ainsi, je demande si c'est une bonne façon de vérifier si un objet est nul:
public List<Object> dataList;
public bool AddData(ref Object data)
bool success = false;
try
{
// I've also used "if (data != null)" which hasn't worked either
if (!data.Equals(null))
{
//NullReferenceException occurs here ...
dataList.Add(data);
success = doOtherStuff(data);
}
}
catch (Exception e)
{
throw new Exception(e.ToString());
}
return success;
}
Si c'est la bonne façon de vérifier si l'objet est nul, que fais-je de mal (comment puis-je empêcher un traitement supplémentaire sur l'objet pour éviter la NullReferenceException)?
c#
null
nullreferenceexception
développeur
la source
la source
throw e;
versusthrow new Exception(e.ToString());
!= null
dans vos vérifications nulles..Equals
générera toujours une exception si l'objet est nul.throw e;
n'est pas beaucoup mieux.throw;
, d'autre part ...e.ToString()
produira une chaîne qui inclut non seulement le message d'erreur, mais aussi ceux de tousInnerExceptions
et la trace de la pile. C'est donc une sorte de message d'exception très lourd. Si vous souhaitez (à juste titre!) Conserver ces informations et les conserver à leur place, utilisez-les simplementthrow;
.Réponses:
Ce n'est pas
data
çanull
, maisdataList
.Vous devez en créer un avec
Encore mieux: puisque c'est un champ, faites-le
private
. Et si rien ne vous empêche, faites-le aussireadonly
. Juste une bonne pratique.De côté
La bonne façon de vérifier la nullité est
if(data != null)
. Ce type de vérification est omniprésent pour les types de référence;Nullable<T>
remplace même l'opérateur d'égalité pour être un moyen plus pratique d'exprimernullable.HasValue
lors de la vérification de la nullité.Si vous le faites,
if(!data.Equals(null))
vous obtiendrez unNullReferenceException
ifdata == null
. Ce qui est assez comique, car éviter cette exception était l'objectif en premier lieu.Vous faites également ceci:
Ce n'est certainement pas bon. Je peux imaginer que vous l'avez mis là juste pour pouvoir pénétrer dans le débogueur tout en restant dans la méthode, auquel cas ignorez ce paragraphe. Sinon, ne prenez pas d'exceptions pour rien. Et si vous le faites, retournez-les en utilisant simplement
throw;
.la source
null != data
. Mettre la constante en premier transforme la typographie boneheadnull = data
en une erreur de compilation, plutôt qu'en une affectation involontaire. (==
if (data = null)
est déjà une erreur de compilation, donc même s'il a fallu des décennies pour y arriver, nous n'avons plus vraiment besoin de faire attention à cela. Même les compilateurs C ++ produiront facilement un avertissement concernant une éventuelle affectation involontaire de ce code.en C #> 7.0 utilisation
if (obj is null)
...Cela ignorera tout == ou! = Défini par l'objet (sauf si vous voulez bien sûr les utiliser ...)
Pour une utilisation non nulle
if (obj is object)
(ouif (!(obj is null))
)la source
obj is not null
)if (obj aint null)
:(if (obj is object)
C # 6 a une vérification nulle monadique :)
avant:
après:
la source
result = myObject == null ? null : myObject.SomeProperty
et votre exemple m'a poussé à écrireresult = myObject?.SomeProperty
. Homme!! C'est sournois. J'adore toujours le codage ...Votre dataList est nulle car elle n'a pas été instanciée, à en juger par le code que vous avez publié.
Essayer:
}
la source
[Modifié pour refléter l'indice par @ kelton52]
La façon la plus simple est de faire
object.ReferenceEquals(null, data)
Puisqu'il
(null==data)
n'est PAS garanti de fonctionner:Produit:
la source
Non, vous devriez utiliser
!=
. Sidata
est en fait null, votre programme se bloquera avecNullReferenceException
un résultat de la tentative d'appel de laEquals
méthodenull
. Sachez également que si vous souhaitez spécifiquement vérifier l'égalité de référence, vous devez utiliser laObject.ReferenceEquals
méthode car vous ne savez jamais commentEquals
a été implémentée.Votre programme plante car il
dataList
est nul car vous ne l'initialisez jamais.la source
Le problème dans ce cas n'est pas que
data
c'est nul. C'est çadataList
lui même est nul.À l'endroit où vous déclarez,
dataList
vous devez créer un nouvelList
objet et l'affecter à la variable.la source
En plus de la réponse @Jose Ortega , il est préférable d'utiliser une méthode d'extension
Et utilisez la
IsNull
méthode pour tous les objets comme:la source
return T == null ? true : false;
et pas seulementreturn T == null;
?Depuis C # 8, vous pouvez utiliser le modèle de propriété 'vide' (avec correspondance de modèle ) pour vous assurer qu'un objet n'est pas nul:
Cette approche signifie " si l'objet fait référence à une instance de quelque chose " (c'est-à-dire qu'il n'est pas nul).
Vous pouvez penser à cela comme le contraire de:
if (obj is null)...
. qui retournera vrai lorsque l'objet ne fait pas référence à une instance de quelque chose.Pour plus d'informations sur les modèles en C # 8.0, lisez ici .
la source
À partir de C # 9, vous pouvez le faire
Pour une utilisation non nulle
Si vous devez remplacer ce comportement, utilisez
==
et en!=
conséquence.la source
Jeffrey L Whitledge a raison. Votre objet `dataList´ lui-même est nul.
Il y a aussi un autre problème avec votre code: vous utilisez le mot-clé ref, ce qui signifie que les données d'argument ne peuvent pas être nulles! Le MSDN dit:
Ce n'est pas non plus une bonne idée d'utiliser des génériques avec le type `Object´. Les génériques doivent éviter la boxe / unboxing et également assurer la sécurité du type. Si vous voulez un type commun, rendez votre méthode générique. Enfin, votre code devrait ressembler à ceci:
la source
Comme d’autres l’ont déjà souligné, il n’est pas,
data
mais plutôt probabledataList
,null
. En plus de ça...catch
-throw
est un antipattern qui me donne presque toujours envie de vomir à chaque fois que je le vois. Imaginez que quelque chose tourne mal au fond de quelque chose quidoOtherStuff()
appelle. Tout ce que vous récupérez est unException
objet, jeté à l'throw
intérieurAddData()
. Aucune trace de pile, aucune information d'appel, aucun état, rien du tout pour indiquer la véritable source du problème, sauf si vous entrez et basculez votre débogueur pour interrompre l'exception levée plutôt que l'exception non gérée. Si vous attrapez une exception et que vous la relancez de quelque manière que ce soit , en particulier si le code dans le bloc try n'est pas trivial, faites-vous (et vos collègues, présents et futurs) une faveur et jetez l'ensembletry
-catch
bloc . Accordé,throw;
est meilleur que les alternatives, mais vous vous donnez toujours (ou à quiconque essaie de corriger un bogue dans le code) des maux de tête complètement inutiles. Cela ne veut pas dire que try-catch-throw est nécessairement mauvais en soi, tant que vous faites quelque chose de pertinent avec l'objet d'exception qui a été jeté à l'intérieur du bloc catch.Ensuite, il y a les problèmes potentiels de capture
Exception
en premier lieu, mais c'est une autre question, d'autant plus que dans ce cas particulier, vous jetez une exception.Une autre chose qui me semble plus que peu dangereuse est qu'elle
data
pourrait potentiellement changer de valeur pendant l'exécution de la fonction, puisque vous passez par référence. Ainsi, la vérification nulle peut réussir, mais avant que le code ne fasse quoi que ce soit avec la valeur, il est changé - peut-être ennull
. Je ne suis pas sûr que ce soit une préoccupation ou non (ce n'est peut-être pas le cas), mais cela semble valoir la peine d'être surveillé.la source
utilisation:
Utilisation conditionnelle:
Mise à jour (d'une autre manière) mise à jour le 31/08/2017. Merci pour le commentaire.
la source
cond ? true : false;
est complètement équivalent à justecond
. Cela n'ajoute rien.return T == null;
aussi renvoie un booléen!return T == null ? true : false;
simplement utiliserreturn T == null;
.Chaque fois que vous créez des objets de classe, vous devez vérifier si l'objet est nul ou non en utilisant le code ci-dessous.
Exemple: object1 est un objet de classe
la source
Je viens de suivre une méthode que nous suivions habituellement en script java. Pour convertir un objet en chaîne, puis vérifiez s’ils sont nuls.
la source
J'ai fait plus simple (façon positive) et ça semble bien fonctionner.
Étant donné que tout type d '"objet" est au moins un objet
la source