C printf спецификатор функции
Мне нужно распечатать значение с плавающей запятой с 16 значащими цифрами.
Прямо сейчас, когда я печатаю, он печатает
то есть 2.555556
когда я хочу его распечатать: 2.555555555555556 /// Всего 16 цифр
Мой спецификатор printf в настоящее время: "%20.18lf"
идеи?
3 ответа
Если значение имеет тип float
вы, вероятно, не получите более 7 значащих цифр после десятичной точки. Если это типа double
, вы можете получить около 15. В зависимости от системы, long double
может быть не более точным, чем double
; по моему, я получаю около 17 значащих цифр после десятичной точки.
В большинстве кодов с плавающей точкой используется тип double
; float
гораздо менее точный и часто не значительно быстрее.
Я немного удивлен, что ты получил 2.555556
а не что-то вроде 2.555555582046508789
с "%20.18lf"
формат.
Кстати, l
(строчная буква L) не обязательна. Формат для double
является "%f"
, а также float
аргументы printf
повышены до double
, так "%f"
правильно для обоих float
а также double
, Формат для long double
является "%Lf"
,
Вот тестовая программа, которую я написал:
#include <stdio.h>
int main(void) {
const float f = 23.0/9.0;
const double d = 23.0/9.0;
const long double ld = 23.0L/9.0L;
printf("%20.18f\n%20.18f\n%20.18Lf\n", f, d, ld);
return 0;
}
и вывод, который я получил на моей системе:
2.555555582046508789
2.555555555555555358
2.555555555555555556
C float или double недостаточно точны, в основном вам нужна функция деления высокой точности. Вот что я написал. Это для целочисленного деления. Возможно, вам придется пересмотреть его для деления поплавка.
int dividend=121, divisor=9;
int quotient,remainder;
//first print out the number before decimal point
quotient=dividend/divisor;
printf("%d", quotient);
remainder=dividend-quotient*divisor;
//print out decimal point
printf(".");
int digit_num=20;//this can be any precision you want
//second we calculate the number after decimal point
for(int i=0;i<digit_num;i++)
{
remainder=remainder*10;
quotient=remainder/divisor;
remainder=remainder-quotient*divisor;
printf("%d", quotient );
dividend=remainder;
}
printf("\n");
printf("%d digits after decimal point has been printed out\n", digit_num );
Следующий код работает хорошо (вы должны включить C99 как %lf
спецификатор не является частью более ранних стандартов):
#include <stdio.h>
int main(void)
{
volatile float v = 2.555555555555556;
printf("%20.18lf\n", v);
return 0;
}
Печатает следующее:
$ gcc -std=c99 -Wall -pedantic -o test ./test.c
$ ./test
2.555555582046508789
$
Если значение короче, скажем, 2,5, оно добавляет его к нулю 2.500000000000000000
,
Таким образом, у вас есть ошибка в другом месте. Как правило, вы должны опубликовать минимальный пример самосогласованного кода, который воспроизводит проблему. В противном случае вы по своему усмотрению.