2 つの極めて小さな数を乗算すると、結果はアンダーフローとなります。
あらかじめ、乗算 (または減算) の被演算子が小さくなり、アンダーフローしそうであることがわかっていれば、計算を倍精度で行い、そのあとで結果を単精度に変換します。
たとえば、ドット積ループは次のようになります。
real sum, a(maxn), b(maxn)
...
do i =1, n
sum = sum + a(i)*b(i)
enddo
|
a(*) と b(*) は、小さな要素が入ることがわかっているので、倍精度で実行し、数値の正確性を保持します。
real a(maxn), b(maxn)
double sum
...
do i =1, n
sum = sum + a(i)*dble(b(i))
enddo
|
このようにすることによって、オリジナルのループが原因であるアンダーフロー頻発をソフトウェア的に解決し、パフォーマンスを上げることができます。しかし、これに関しては、確実で手間のかからない方法はありません。計算が多いコードを使用するユーザー自身の経験のほうが、より適切な解決策を決定することでしょう。