一个简单的解决方案是先通过 x 槽
sprintf
,然后通过 strtod
(产生 y),直到 x = y:
#include <float.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#define PREC_MAX 256
void print_f(double x, bool newline)
{
double y;
char s[PREC_MAX * 3]; // what is the precise multiplier ?
bool f_printed = false;
for (int prec = 1; prec < PREC_MAX; ++prec)
{
if (sprintf(s, "%.*f", prec, x) > 1) // may encoding error occur ?
{
y = strtod(s, 0); // is there a real need of error handling ?
if (x == y)
{
printf("%s", s);
f_printed = true;
break;
}
}
}
if (!f_printed)
{
printf("%.*g\n", DBL_DECIMAL_DIG, x);
}
if (newline)
{
printf("\n");
}
}
int main(void)
{
print_f(0.000000000000000000000001617, true); // 0.000000000000000000000001617
print_f(1.0, true); // 1.0
print_f(0x1p-27, true); // 0.000000007450580596923828
}