1

浮動小数点演算のキャンセルに問題があります。問題がどこにあるのかはわかっていますが、効率的な解決策が思いつきません。

ここに私の問題があります: 私は 3D で粒子シミュレーションを行っているので、各粒子には 3 つの座標 (x、y、z) があります。ドメイン全体がサブセルに分割されます。ある時点で、粒子があるタイムステップにあるサブセルの ID を計算します。これは簡単な式です。

   int cellOffset_y = (pos[1] - y_min) / cellWidth_y;

pos[1] は粒子の x 座標、y_min はドメインの開始点、cellWidth はセルの幅です。

ここに私の問題があります: 私は、粒子の座標が 0 であるべきテストケースを持っています。-3e-18. この式を使用すると、キャンセルにより-3e-18がドロップします。ここでの大きな問題は、パーティクルの位置が負であり、境界線が正確に 0 であるため、パーティクルが実際にあるセル ID とは異なるセル ID が返されることです。

では、この問題を解決する方法を知っている人はいますか? 明確に記載されていることを願っています

4

1 に答える 1

2

基本的に 2 つの選択肢があります (「問題を抱えて生きる」ことを有効な選択肢と見なす場合は、3 つです!):

  1. アップストリームのある程度の不正確さを許容するために、グリッドの境界線を少しずらします。したがって、 の(pos - y_min + k) / width小さな値の場合、計算は になりますk

    もちろん、これは逆方向に発生するエラー (つまり、少し大きすぎる数値) には対応していません。実際、これはその状況を悪化させます。しかし、この問題を解決する一般的な方法はありません。あなたのコードは、 -3e-18 が正しいか、少し間違っているかを「知る」ことができません!

  2. アップストリームの計算を修正します。

于 2013-03-06T20:01:11.013 に答える