2016-11-04 3 views
1

Lors de la conversion de double (ou float) en decimal, des exceptions de débordement sont possibles. J'ai donc écrit cette petite méthode d'extension qui empêche ce en saturant:Éviter OverflowException lors de la conversion du double en nombre décimal

public static decimal ToDecimalSafe(this double input) 
{ 
    try 
    { 
     return (decimal)input; 
    } 
    catch (OverflowException) 
    { 
     if (input < 0) 
      return decimal.MinValue; 
     else 
      return decimal.MaxValue; 
    } 
} 

La question est, ce débordement se produit assez souvent dans mon cas d'utilisation, brisant les lignes directrices « exceptions devraient être exceptionnelles ». Cela ralentit l'application, oui, mais ce n'est pas très important. Le vrai problème est qu'il provoque également beaucoup d'exceptions de première chance pendant le débogage, ce qui est ennuyeux. Voici le numéro de tentative de deux, ce qui semble fonctionner très bien:

public static decimal ToDecimalSafe(this double input) 
{ 
    if (input < (double)decimal.MinValue) 
     return decimal.MinValue; 
    if (input > (double)decimal.MaxValue) 
     return decimal.MaxValue; 

    try 
    { 
     return (decimal)input; 
    } 
    catch (OverflowException) 
    { 
     if (input < 0) 
      return decimal.MinValue; 
     else 
      return decimal.MaxValue; 
    } 
} 

J'ai quitté le try-catch pour vous assurer que je prends des cas limites possibles. La question est la suivante: y a-t-il des cas limites ou puis-je simplement omettre le try-catch?

Un double peut-il être >= (double)decimal.MinValue et <= (double)decimal.MaxValue et provoquer un débordement lors de la conversion?

+0

Si cela arrive assez souvent, pourquoi diable utilisez-vous 'decimal' plutôt que' double' en premier lieu? Il semble que vous utilisiez «décimal» pour des calculs scientifiques ou d'ingénierie plutôt que financiers - ce qui n'est pas la bonne chose à faire. –

+0

@MatthewWatson Ce n'est rien de très précis ou quoi que ce soit. C'est juste pour interagir entre certains matériels qui traitent des doubles et des paramètres fournis par l'utilisateur et utilisant des décimales. Le matériel fournit des limites, qui ont souvent une portée ridiculement grande dont l'utilisateur ne se soucie pas de toute façon. –

+0

@MatthewWatson "Assez souvent" ne signifie pas 1000 fois par seconde, cela signifie 100 fois au total lorsque vous saisissez ces limites de réglage. –

Répondre

1

L'exception ne se produira plus. Vous pouvez modifier votre code de cette manière.

public static decimal ToDecimalSafe(this double input) 
{ 
    if (input < (double)decimal.MinValue) 
     return decimal.MinValue; 
    else if (input > (double)decimal.MaxValue) 
     return decimal.MaxValue; 
    else 
     return (decimal)input; 
} 

Vous pouvez également utiliser la méthode de conversion spécifique, mais il n'empêche pas l'exception

Convert.ToDecimal

Si votre problème est juste la pause de débogage qui est ennuyeux alors je suggère de jeter un oeil à [DebuggerStepThrough] ou [DebuggerHidden] attributs

+0

Je n'avais aucune idée de ces attributs, merci. Très utile. BTW, je viens de passer quelques minutes en essayant de comprendre cela par moi-même et il semble que donner (double) decimal.MinValue ou (double) decimal.MaxValue en entrée soulève l'exception. Faire les comparaisons inclusives (<= and > =) résout le problème, mais je vais devoir trouver comment trouver une valeur qui est légèrement dans les limites pour voir si cela se bloque. –