2017-10-23 13 views
0

私はミリ秒単位のタイムスタンプで受信したデータを記録する必要があるアプリケーションを作成しています。これはこれは、浮動小数点加算が正しく機能しない

D = 84137605.580233 F1 = 84137608.000000 F2 = 84137000.000000 F3 = 605.580200 F4 = 84137608.000000

しかし、ここでは、二重変数の出力を印刷してしまったサンプル出力である私のコード

struct timespec ts; 
struct tm tt; 

clock_gettime(CLOCK_REALTIME,&ts); 
localtime_r(&ts.tv_sec,&tt); 

double d=(tt.tm_hour*3600+tt.tm_min*60+tt.tm_sec)*1000.0+ts.tv_nsec/1000000.0; 
float f1=(tt.tm_hour*3600+tt.tm_min*60+tt.tm_sec)*1000.0f+ts.tv_nsec/1000000.0f; 
float f2=(tt.tm_hour*3600+tt.tm_min*60+tt.tm_sec)*1000.0f; 
float f3=ts.tv_nsec/1000000.0f; 
float f4=f2+f3; 

printf("d=%lf\tf1=%f\tf2=%f\tf3=%f\tf4=%f\n",d,f1,f2,f3,f4); 

ですdとfloat変数f1 & f4は異なります。誰かが私にこの理由を教えてもらえますか?

+0

これは 'float'と' double'がすべての実数を正確に表すことができないため、標準的な精度の問題のようです。 – templatetypedef

+1

簡単な答えですが、浮動小数点数は7〜8桁の精度しかありません。あなたはこれを超えています。ここで浮動小数点ロジックを使用することはお勧めできません。代わりに、固定小数点represntaitionを使用することを検討してください。 –

+0

@ ConstantineGeorgiou Seconded。また、[浮動小数点値を追加しない](http://www.volkerschatz.com/science/float.html) – DevNull

答えて

1

84137605は16進数で0x503D685なので、完全精度で表現するには27ビット必要です。 IEEE浮動小数点数は24ビットの精度(23の小数ビットと1つの隠れビット)を持っています。だから、あなたは失う。

関連する問題