4

小数点以下2桁を除算して、結果を表示しようとすると問題が発生します。迷惑なことに、これはサーバーでのみ発生しており、コードをローカルで実行すると完全に正常に機能しているように見えます。これは私が実行しようとしているコードです


decimal dOne = -966.96M;
decimal dTwo = 2300M;

decimal dResult = Decimal.Round((dOne / dTwo), 28, 
                               MidpointRounding.AwayFromZero);

結果の数値(Windows計算機から生成されたもの)は次のとおりです。

-0.43346086956521739130434782608696

これにより、常にオーバーフロー例外が発生します。

System.OverflowException: Value was either too large or too small for a Decimal.
   at System.Decimal.FCallDivide(Decimal& result, Decimal d1, Decimal d2)
   at System.Decimal.op_Division(Decimal d1, Decimal d2)

結果の数値は小数点以下32桁を超え、小数点以下は28桁までしか保持できないため、これはある程度意味があります。ただし、結果が小数点以下に格納されているように見えるため、この除算を実行する方法がわかりません。四捨五入して格納する前に、メモリに入力します。また、小数で格納するのではなく、文字列に直接変換しようとしましたが、同じ問題があります。

何か案は?私は明らかにばかげたことをしましたか(おそらく)、この計算を実行するためのより良い方法はありますか?

4

4 に答える 4

4

それはうまくいくはずです。分割が正確なバージョンを返すことは保証されていません。たとえば、1/3mは正常に機能します。

結果は明らかにの範囲外ではないdecimalので、サーバーで何か奇妙なことが起こっているように見えます。

確認すべきことDecimal.Roundの1つは、例外をスローしているのか、それとも部門自体をスローしているのかということです。それらを別々のステートメントに入れて調べてください。

于 2010-07-08T13:24:15.203 に答える
4

計算する前にに変換してみてください。必要に応じて、後でdoubleに戻ってください。decimal

decimal dOne = -966.96M;
decimal dTwo = 2300M;

double one = (double)dOne;
double two = (double)dTwo;

double result = one / two;

decimal dResult = (decimal)result; // Additional rounding may be necessary
于 2010-07-08T13:24:56.043 に答える
1

私はDecimal.RoundReflectorを介して見ましたが、それがスローされることはないOverflowExceptionので、例外は部門からのものであると確信しています。スタックトレースを含めるように回答を編集できますか?

また、分子と分母があなたが書いたものとまったく同じであることを絶対に確信していますか?例外が発生したときに、それらをコンソールまたはログファイルまでトレースしてみてください。

あなたはこのようなことをすることができます:

decimal dOne = -966.96M; 
decimal dTwo = 2300M;  
try
{
  decimal dResult = Decimal.Round((dOne / dTwo), 28, MidpointRounding.AwayFromZero); 
}
catch (OverflowException)
{
  Console.WriteLine(dOne);
  Console.WriteLine(dTwo);
}

編集:FCallDivide SSCLIでコードを見つけたと思います。ただし、.NET Frameworkのリリースバージョンでは異なる可能性がありますが、SSCLIで行われた方法から、オーバーフロー例外がさまざまな方法で生成されることがわかります。コードは非常に複雑です。問題を示す短いが完全なプログラムを作成できれば、それをバグとしてMicrosoftに提出します。これらの入力には、アルゴリズムを混乱させる特定のビットパターンがある可能性があります。

于 2010-07-08T13:37:22.847 に答える
1

サーバーで発生した場合(デバッグできない場合)。問題がこれらの線の範囲内にあることを本当に確信していますか?

たぶん、単一のDecimal.Roundステートメントのみの周りにtry-catchステートメントを配置し、代わりに奇妙な値を返すことができます。このコードをサーバーで再度実行して、このcatchステートメントが実際に呼び出されるかどうか、または例外が別の場所で発生する可能性があるかどうかを確認できます。

于 2010-07-08T13:43:40.913 に答える