だから私は2つの変数を持つプログラムを実行しようとしています.1つの変数が別の変数と等しい場合、関数を実行します. この場合、印刷スパムです。ただし、何らかの理由で、このプログラムを実行すると、それらが等しいことがわかっているにもかかわらず、出力が得られません。
g=0.0
b=3.0
while g < 30.0:
if g==b:
print "Hi"
g+=.1
print g, b
だから私は2つの変数を持つプログラムを実行しようとしています.1つの変数が別の変数と等しい場合、関数を実行します. この場合、印刷スパムです。ただし、何らかの理由で、このプログラムを実行すると、それらが等しいことがわかっているにもかかわらず、出力が得られません。
g=0.0
b=3.0
while g < 30.0:
if g==b:
print "Hi"
g+=.1
print g, b
.1 を 0.0 に十分な回数追加すると 3.0 が生成されると想定しています。これらは浮動小数点数であり、不正確です。丸め誤差により、値が正確に 3.0 になることはありません。==
浮動小数点数のテストに使用することはほとんどありません。
これを行う良い方法は、整数値でカウントし (たとえば、0 から 300 までの i を 1 ずつループする)、浮動小数点値が使用されている場合にのみカウンタをスケーリングすることです (たとえば、f = i * .1 を設定します)。これを行うと、ループ カウンターは常に正確であるため、必要な反復が正確に得られ、反復ごとに累積されない浮動小数点の丸めが 1 つだけになります。
ループ カウンターは最も一般的には整数型であるため、(オーバーフローに達するまで) 加算が正確であることが容易にわかります。ただし、ループ カウンターの値と演算が正確であることが確実であれば、ループ カウンターは浮動小数点型の場合もあります。(一般的な 32 ビット浮動小数点形式は、正確に -2 24から +2 24までの整数を表します。それ以外では、整数を正確に表す精度がありません。正確に .1 を表していないため、インクリメントで数えることはできません。 .1 の.しかし、.5、.25、.375、または正確に表される適切な 2 の累乗の他の小さな倍数で数えることができます。)
Karoly Horvath のコメントを拡張すると、ほぼ等しいかどうかをテストするためにできることは、最小増分に対して非常に小さい値 (イプシロンと呼びましょう) を選択することです。イプシロンが 1.0 * 10^-6 であり、インクリメントよりも 5 桁小さいとしましょう。(おそらく、浮動小数点表現の平均丸め誤差に基づいているはずですが、それはさまざまであり、これは単なる例です)。
次に行うことは、g と b が異なるイプシロン未満であるかどうかを確認することです。それらが実質的に等しいほど十分に近い場合、実際と実際の差は、イプシロンで近似している丸め誤差です。
チェック
abs(g - b) < epsilon
ほとんどの場合、ほとんどの場合、十分ではありませんが、同等性チェックが行われます。