10

非常に小さい、ほぼゼロの数値を生成しているように見える数学 (C++) があります (trig 関数呼び出しが私の本当の問題であると思われます) が、これらのケースを検出して、もっと詳しく。

現在、以下を試していますが、正しいですか?

if ( std::abs(x) < DBL_MIN ) {
     log_debug("detected small num, %Le, %Le", x, y);
}

第二に、数学の性質は本質的に三角関数です(別名、多くのラジアン/度変換および//呼び出しsinなどを使用します)。数学的なエラーを回避するには、どのような変換を行うことができますか?costan

明らかに、乗算には対数変換を使用できます-他に何がありますか?

4

4 に答える 4

5

広く信じられていることとは反対に、は正の最小値でDBL_MINはなく、正規化された正の最小値です。通常、64 ビットの ieee754の場合は 2 -1022ですが、最小の正の値は 2 -1074です。したがってdouble doubledoublesdouble

現在、以下を試していますが、正しいですか?

if ( std::abs(x) < DBL_MIN ) {
     log_debug("detected small num, %Le, %Le", x, y);
}

肯定的な答えがあるかもしれません。xこの条件は、 が非正規化された (サブノーマルとも呼ばれる) 数か ±0.0かをチェックします。あなたの特定の状況について詳しく知らなければ、そのテストが適切かどうかはわかりません. 非正規化された数値は、正しい結果が 0 になる計算の正当な結果、または丸めの結果である可能性があります。また、丸めによって、数学的に正しい結果が 0 になる場合よりもはるかに大きな数値が生成される可能性もあるDBL_MINため、はるかに大きなしきい値を設定することもできます。賢明です。

于 2012-02-17T22:15:44.070 に答える
2

がdoubleの場合、このアプローチの1つの問題は、正当にゼロであるか、。よりも小さい正の値でxあるかを区別できないことです。したがって、これは、合法的にゼロになることは決してないことがわかっていて、アンダーフローがいつ発生するかを確認したい場合に機能します。xxDBL_MINx

信号をキャッチしてみることもできますSIGFPE。これは、浮動小数点アンダーフローなどの数学エラーが発生したときに、POSIX準拠のシステムで起動します。参照: http: //en.wikipedia.org/wiki/SIGFPE

編集:明確にDBL_MINするために、それはdoubleが保持できる最大の負の値ではなく、doubleが保持できる最小の正の正規化された値です。したがって、値をゼロにできない限り、アプローチは問題ありません。

もう1つの有用な定数はDBL_EPSILON、1.0を戻さずに1.0に追加できる最小のdouble値です。これは。よりもはるかに大きい値であることに注意してくださいDBL_MIN。ただし、0ではなく1に向かう三角関数を実行しているので、便利な場合があります。

于 2011-08-08T12:48:23.650 に答える
2

C++ を使用しているため、最も慣用的なのはstd::numeric_limitsfrom headerを使用すること<limits>です。

例えば:

template <typename T>
bool is_close_to_zero(T x)
{
    return std::abs(x) < std::numeric_limits<T>::epsilon();
}

大きく使用される実際の許容範囲は、問題によって異なります。回答を強化できるように、具体的なユースケースで質問を完了してください。

std::numeric_limits<T>::min()あり、std::numeric_limits<T>::denorm_min()それは役に立つかもしれません。最初のものは型の非正規化されていない最小の正の値 ( fromTに等しい) であり、2 番目のものは型の最小の正の値(同等のものはありません) です。FLT/DBL/LDBL_MIN<cfloat>T<cfloat>

[このドキュメントは、浮動小数点数の表現に慣れていない場合に読むと便利です。]

于 2011-08-08T13:12:22.047 に答える
0

最初のifチェックは、値がゼロの場合にのみ真になります。

2 番目の質問では、多くのコンバージョンが発生していることを暗示しています。代わりに、1 つの単位 (度またはラジアン) を選択し、その単位ですべての計算操作を行います。次に、必要に応じて、最後に他の値への単一の変換を行います。

于 2011-08-08T13:31:19.253 に答える