Причина, по которой они производят одинаковое количество десятичных разрядов, заключается в том, что 6
является значением по умолчанию. Вы можете изменить это, как в отредактированном примере ниже, где синтаксис %.*f
. *
может быть числом, показанным ниже, или во втором случае, представленным в качестве другого аргумента.
#include <stdio.h>
int main(void) {
int a = 960;
int b = 16;
float c = a*0.001;
float d = a*0.001 + b;
double e = a*0.001 + b;
printf("%.9f\n", c);
printf("%.*f\n", 9, d);
printf("%.16f\n", e);
}
Вывод программы:
0.959999979
16.959999084
16.9600000000000009
Дополнительные десятичные разряды теперь показывают, что ни один из результатов не является точным. Одна из причин в том, что 0.001
нельзя точно закодировать как значение с плавающей запятой. Есть и другие причины, которые были подробно рассмотрены.
Один простой способ понять, почему float
имеет около 2^32
различных значений, которые могут быть закодированы, однако в диапазоне float
существует бесконечность действительных чисел, и только около 2^32
из них можно представить точно . В случае дроби 1/1000
в двоичном виде это повторяющееся значение (как и дробь 1/3
в десятичной дроби).