Question

Je travaille sur un projet dans lequel je constate que je vérifie les éléments suivants dans de très nombreux endroits:

if(item.Rate == 0 || item.Rate == null) { }

plus comme une curiosité qu'autre chose, quel est le meilleur moyen de vérifier les deux cas?

J'ai ajouté une méthode d'assistance qui est:

public static bool nz(object obj)
{
    var parsedInt = 0;
    var parsed = int.TryParse(obj.ToString(), out parsedInt);
    return IsNull(obj) || (parsed && parsedInt == 0);
}

Y a-t-il un meilleur moyen?

Était-ce utile?

La solution

J'aime if ((item.Rate ?? 0) == 0) { }

Mise à jour 1:

Vous pouvez également définir une méthode d'extension telle que:

public static bool IsNullOrValue(this double? value, double valueToCheck)
{
    return (value??valueToCheck) == valueToCheck;
}

Et utilisez-le comme ceci:

if(item.IsNullOrValue(0)){} // mais vous n'en tirez pas grand chose

Autres conseils

Utilisation des génériques:

static bool IsNullOrDefault<T>(T value)
{
    return object.Equals(value, default(T));
}

//...
double d = 0;
IsNullOrDefault(d); // true
MyClass c = null;
IsNullOrDefault(c); // true

Si T c'est un type de référence , value sera comparé à null (default(T)), sinon, si value type est un default(t), disons double , false est 0d, pour bool est '\0', pour char est <=> et ainsi de suite ...

Bien que j'aime bien la réponse acceptée, je pense que, pour être complet, cette option devrait également être mentionnée:

if (item.Rate.GetValueOrDefault() == 0) { }

Cette solution

& # 185; Cela ne devrait toutefois pas influer sur votre décision, car ce type de micro-optimisation ne fera probablement aucune différence.

Il s’agit en réalité d’une extension de la réponse acceptée par Freddy Rios, qui utilise uniquement des médicaments génériques.

public static bool IsNullOrDefault<T>(this Nullable<T> value) where T : struct
{
    return default(T).Equals( value.GetValueOrDefault() );
}

public static bool IsValue<T>(this Nullable<T> value, T valueToCheck) where T : struct
{
    return valueToCheck.Equals((value ?? valueToCheck));
}

REMARQUE , nous n'avons pas besoin de vérifier la valeur null par défaut (T), car nous avons affaire à des types de valeur ou à des structs! Cela signifie également que nous pouvons supposer que T valueToCheck ne sera pas nul; Tu te souviens ici que T? est un raccourci Nullable < T > donc en ajoutant l'extension à Nullable < T > nous obtenons la méthode dans int ?, double ?, bool? etc.

Exemples:

double? x = null;
x.IsNullOrDefault(); //true

int? y = 3;
y.IsNullOrDefault(); //false

bool? z = false;
z.IsNullOrDefault(); //true

Je suis d'accord avec l'utilisation de la ?? opérateur.

Si vous traitez avec des chaînes, utilisez if (String.IsNullOrEmpty (myStr))

  

Y a-t-il un meilleur moyen?

Eh bien, si vous cherchez vraiment un meilleur moyen, vous pouvez probablement ajouter une autre couche d’abstraction au-dessus de Rate. Eh bien voici quelque chose que je viens de proposer avec Nullable Design Pattern.

using System;
using System.Collections.Generic;

namespace NullObjectPatternTest
{
    public class Program
    {
        public static void Main(string[] args)
        {
            var items = new List
                            {
                                new Item(RateFactory.Create(20)),
                                new Item(RateFactory.Create(null))
                            };

            PrintPricesForItems(items);
        }

        private static void PrintPricesForItems(IEnumerable items)
        {
            foreach (var item in items)
                Console.WriteLine("Item Price: {0:C}", item.GetPrice());
        }
    }

    public abstract class ItemBase
    {
        public abstract Rate Rate { get; }
        public int GetPrice()
        {
            // There is NO need to check if Rate == 0 or Rate == null
            return 1 * Rate.Value;
        }
    }

    public class Item : ItemBase
    {
        private readonly Rate _Rate;
        public override Rate Rate { get { return _Rate; } }
        public Item(Rate rate) { _Rate = rate; }
    }

    public sealed class RateFactory
    {
        public static Rate Create(int? rateValue)
        {
            if (!rateValue || rateValue == 0) 
                return new NullRate();
            return new Rate(rateValue);
        }
    }

    public class Rate
    {
        public int Value { get; set; }
        public virtual bool HasValue { get { return (Value > 0); } }
        public Rate(int value) { Value = value; }
    }

    public class NullRate : Rate
    {
        public override bool HasValue { get { return false; } }
        public NullRate() : base(0) { }
    }
}

Votre exemple de code échouera. Si obj est null, alors obj.ToString () donnera une exception de référence null. Je raccourcirais le processus et rechercherais un obj nul au début de votre fonction d'assistance. En ce qui concerne votre question, quel est le type que vous recherchez pour null ou zéro? Sur String, il existe une excellente fonction IsNullOrEmpty. Cela me semble une excellente utilisation des méthodes d'extension pour implémenter une méthode IsNullOrZero sur l'int? type.

Edit: Rappelez-vous, le '?' est juste un sucre de compilateur pour le type INullable, vous pouvez donc probablement prendre un INullable comme paramètre puis jsut le comparer à null (parm == null) et, si ce n’est pas nul, comparer à zéro.

public static bool nz(object obj)
{
    return obj == null || obj.Equals(Activator.CreateInstance(obj.GetType()));
}
class Item{  
 bool IsNullOrZero{ get{return ((this.Rate ?? 0) == 0);}}
}

N'oubliez pas que pour les chaînes, vous pouvez toujours utiliser:

String.IsNullOrEmpty(str)

Au lieu de:

str==null || str==""

Encore un peu plus loin que Joshua Shannon réponse . Désactivez maintenant la prévention boxing / unboxing :

public static class NullableEx
{
    public static bool IsNullOrDefault<T>(this T? value)
        where T : struct
    {
        return EqualityComparer<T>.Default.Equals(value.GetValueOrDefault(), default(T));
    }
}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top