Vous écrivez une expression booléenne qui pourrait ressembler à ceci:
team.Category == "A Team" && team?.Manager?.IsVietnamVet
public class Manager
{
public bool IsVietnamVet { get; set; }
}
public class Team
{
public string Category { get; set; }
public Manager Manager { get; set; }
}
... et vous obtenez une erreur:
L'opérateur '&&' ne peut pas être appliqué aux opérandes de type 'bool' et 'bool?'
Quelle est la manière optimale / la plus propre de le gérer?
team.Category == "A Team" && (team?.Manager?.IsVietnamVet ?? false)
Est-ce vraiment lisible?
team.Category == "A Team" && (team?.Manager?.IsVietnamVet).GetValueOrDefault()
Cela peut ne pas fonctionner dans LINQ-to-Entities ...
team.Category == "A Team" && team?.Manager?.IsVietnamVet == true
Souhaitez-vous vraiment écrire
if (condition == true)
sans aucune hésitation?
Il y a-t-il des alternatives? Est-il finalement préférable d'écrire:
team.Category == "A Team" && team.Manager != null && team.Manager.IsVietnamVet
team.Manager?.IsVietnamVet
, c'est-à-dire aucune conditionnelle nulle aprèsteam
, car elle ne peut déjà l'êtrenull
.nullableBool == true
teste essentiellementnullableBool != false && nullableBool != null
(et c'est cette deuxième partie qui la rend utile et donc pas superflue)nullableBool == true
si je ne crée pas de wrapper. Il est lisible car vous n'écrivez normalement pas== true
lorsque vous utilisez un booléen ordinaire comme le mentionne @Flater, il suggère donc que la variable est nullable. De plus, cela améliore la lisibilité de LINQ car vous n'utilisez pas plusieurs conditions nulles comme le mentionne @Fabio.Réponses:
Dans ce cas particulier, il pourrait être judicieux de suivre la loi de Déméter, c'est-à-dire
Plus généralement, si une expression booléenne est complexe ou moche, il n'y a rien à dire que vous ne pouvez pas la diviser (ou une partie) en une instruction distincte:
Lorsque vous parcourez le code dans le débogueur, il est souvent plus agréable d'avoir des conditions élaborées empaquetées en une seule
bool
juste pour économiser un peu de survol de la souris; en fait, il serait peut-être plus agréable de mettre le tout dans unebool
variable.ou avec LINQ:
la source
a && b && c &&...
sont exécutés séquentiellement, et le suivant n'est même pas exécuté si le précédent l'estfalse
. Donc, les gens mettent généralement le plus vite au début. Gardez cela à l'esprit lorsque vous déplacez des choses dans un bool-varIsManagerVietnamVet
propriété va vérifier dans une base de données;)Je pense que l' option 3 (c. -à-
== true
) est la plus propre moyen de test unbool?
esttrue
, parce qu'il est très clair sur ce qu'il fait.Dans la plupart des codes, cela
x == true
n'a pas de sens, car c'est la même chose quex
, mais cela ne s'applique pas ici, donc je pense que== true
ce ne serait pas très déroutant.la source
a?.b == true
qu'il sera confus, mais une fois qu'il comprend ce qu'il fait, cela devient un idiome très lisible, bien plus agréable que de devoir tester!= null
au milieu d'une expression complexe. Même chose poura?.b ?? false
, qui semble avoir gagné en popularité comme solution la plus populaire, car elle correspond à ce que vous saisiriez si vous aviez affaire à un type autre que booléen [bien que je n'aime pas cela pour booléen; pour moi, ça ne se lit pas aussi naturellement; Je préfère== true
].S'étendant sur la réponse de Ben Cottrell, le motif "Null Object" peut vous aider davantage.
Au lieu de renvoyer une
null
équipe / un gestionnaire, extrayezITeam
etIManager
interfacez et renvoyez des implémentations alternatives significatives:Ensuite, tout d'un coup, vous pouvez le faire en
team.ManagedByVietnamVet
toute sécurité.Bien sûr, cela dépend du fournisseur en amont de
team
pour être null-safe - mais cela peut être assuré avec des tests appropriés.la source
J'ai écrit une classe simple que vous pourriez utiliser:
S'il est fiable d'utiliser un type personnalisé, bien sûr. Vous pouvez comparer
MyBool
avec les deuxbool
etNullable<bool>
.la source