次の式が使用される C++ アプリ (Windows 7、64 ビット、VS 2008) を開発します (すべての変数は double 型です)。
mValue = floor(mValue/mStepping)*mStepping;
アイデアは、数値を指定された小数点以下の桁数に短縮することです。これを行うためのより良い方法があると思いますが、これはここでの質問ではありません (しかし、より良いオプションがある場合は、それを取り入れてください!)。
mValue はユーザー入力から取得されるため、ほとんどの場合、小数点以下の桁数は問題ありません。ただし、出力が入力と異なる場合もあります。
たとえば、mStepping の値は 0.1 です (小数点以下 1 桁に丸める必要があります)。mValue の値が 14.6 であれば、すべて問題ありません。mValue が 14.7 の場合、結果は 14.6 です。
では、なぜ floor(14.7/0.1)*0.1 = 14.6 なのですか?
他の値をテストしたところ、それらの約 20% で 0.1 の差がありました。さらに調べてみると、14.7/0.1 には 147.0 とは異なるバイナリ エンコーディングがあることがわかりました。
14.7/0.1 = ff ff ff ff ff 5f 62 40
147.0 = 00 00 00 00 00 60 62 40
同じ数値が double として別の方法でエンコードされる可能性があることを理解しています。しかし、なぜ floor() はそれらを異なる方法で処理するのでしょうか? そして、私はそれに対して何ができますか?