I was able to compile xnec2c with long double
's by simply search-replacing double
with long double
. It calculates correctly, except anywhere that a format specifier is used because it wants %Lf
... and of course GCC is barking quite a bit about -Wformat=
after hacking it in with this one-liner:
perl -p -i -e 's/_Complex/complex/g; s/gdouble/double/g; s/([ \t(]|^)double/$1long double/g' src/*.[ch]
Ultimately the goal is to:
double
's with typedef double xnec2c_double_t
./configure --enable-long-double
option in configure.ac
that adjusts the typedef to long double
.printf
's and related format specifier-based functions (like sprintf
, etc).Question:
What are the best practices for making format specifiers work with compile-time selection of double
vs long double
by changing the typedef
?
I could go put #ifdef
's around every print, or #define SPEC_DOUBLE "%Lf"
and string-concatenate as printf("foo=" SPEC_DOUBLE "\n", foo)
but that seems almost as hackish as adding #ifdef
's around every printf
. A my_smart_printf
macro could be an option if there is an elegant way to do it, but I've not come up with one.
Is there a "good" way to do this?
Nota bene:
How do you support both doubles and long doubles without changing format specifiers in C?
Convert the floating point argument to long double
and use matching long double
specifiers so the same format can be used in all cases.
printf("%Lf\n", (long double) float_or_double_or_long_double_object);
Follow the PRI...
example from <inttypes.h>
and create your own specifier as in #define SPEC_DOUBLE "Lf"
. Note no "%"
.
printf("%" SPEC_DOUBLE "\n", xnec2c_double_object);
Create a helper function to convert your special floating point into a string.
extern char *xnec2c_to_str(char *dest, xnec2c_double_t x);
// - digits . frac \0
#define xnec2c_STR_SZ (1 + (LDBL_MAX_10_EXP+1) + 1 + 6 + 1)
#define xnec2c_TO_STR(x) (xnec2c_to_str((char[xnec2c_STR_SZ]){ 0 }, x)
printf("%s\n", xnec2c_TO_STR(x));
And now for something completely different, consider Formatted print without the need to specify type matching specifiers.