輸入浮點數後輸出發現數值不一致,即使未超過 FLT_DIG (6~7 位) 宣稱的有效數字。測試代碼:
#include <stdio.h>
#include <float.h>
int main(void) {
float test;
char data[7];
printf("Float has at least %d effective numbers\n", FLT_DIG);
printf("Then i'm gonna check it!\n");
printf("test data:_______\b\b\b\b\b\b\b");
scanf("%f", &test);
printf("please input again to confirm it:_______\b\b\b\b\b\b\b");
scanf("%s", &data);
printf("So %f is supposed to be %s", test, data);
return 0;
}
十進制小數無法精確轉換為二進制浮點數。IEEE 754 單精度(float)結構:
十進制 0.1、0.2 等常見數值在二進制中為無限循環小數,截斷後產生誤差。例如:
float x = 0.51f; // 二進制無法精確表示
float y = 0.5f; // 二進制精確表示為 0.1
printf("x=%.8f y=%.8f", x, y); // 輸出 0.50999999 0.50000000
FLT_DIG = 6 表示:任意 6 位有效十進制數字轉為 float 再轉回十進制,能保證原值不變。但單個數值的轉換誤差可能導致第 7 位發生變化,且累積運算會放大誤差。
printf("%.2f", val) 限制輸出位數,掩蓋尾部噪聲。decNumber、Java BigDecimal 實現十進制精確運算。浮點運算本質上是近似計算。理解「機器數」與「真值」的差異,掌握誤差分析方法(絕對誤差、相對誤差、機器 epsilon),才能編寫健壯的數值計算程序。