This is totally pointless when serialization to and from an unsigned integer that's binary equivalent would be perfectly reversible and therefore wouldn't lose any information.
double f = 0.0/0.0; // might need some compiler flags to make this a soft error.
double g;
char s[9];
assert(sizeof double == sizeof uint64_t);
snprintf(s, 9, "%0" PRIu64, *(uint64_t *)(&f));
snscanf(s, 9, "%0" SCNu64, (uint64_t *)(&g));
If you want something shorter, apply some sort of heuristic that doesn't sacrifice faithful reproduction of the original representation, e.g., idempotency.
As written, it is UB, yes, but certainly in C++, and, I think, also in C, using a union is undefined behavior, too. I think (assuming isn’t and float to be of the same size) the main risk is that, if you do
union {
float f;
int i;
} foo;
foo.f = 3.14;
printf(“%x”, foo.i);
that the compiler can think the assignment to foo.f isn’t used anywhere, and thus can chose not to do it.
In C++, you have to use memmove (compilers can and often do recognize that idiom)
If the goal is just to reliably serialize and deserialize floating point numbers, use `%a` instead. It will print and read hexadecimal floating point literals.
This is totally pointless when serialization to and from an unsigned integer that's binary equivalent would be perfectly reversible and therefore wouldn't lose any information.
If you want something shorter, apply some sort of heuristic that doesn't sacrifice faithful reproduction of the original representation, e.g., idempotency.