Re: Convert float to its corresponding bytes?
This is really a particluar need, Can it be done otherwise, i.e. reject the proposed solution and look again to the problem, because, although it was done, it does not make such sens for the "Why?" question.
Re: Convert float to its corresponding bytes?
the reason I thought this way, was because I translated the Nim code in my head to C, to something like that: void flt2arr(double x, uint8_t[] result) { for(int i = 0; i < 8; i++) result[i] = (uint8_t*) + i; } Run But as @araq said, this is not what the output of the Nim compiler is
Re: Convert float to its corresponding bytes?
Does it also use an union when compiling to C++?
Re: Convert float to its corresponding bytes?
In C99 (ISO/IEC 9899:1999 6.5/7; the exact same wording is used in ISO/IEC 9899:2011 ยง6.5/7) > An object shall have its stored value accessed only by an lvalue expression > that has one of the following types ... a character type. The meaning of "a character type" here includes unsigned char, which is also uint8. So, making some assumptions about the Nim code generator, both approaches are well defined in C.
Re: Convert float to its corresponding bytes?
The following should also be safe, this translates to a memcpy() at the C level. This may seem like overkill, but the C compiler should recognize the use of memcpy for type punning and optimize it away and generate a register to register move. proc flt2arr(f: var float64, a: var array[8, uint8]) = assert sizeof(a) == sizeof(f) copyMem(addr a[0], addr f, sizeof f) proc arr2flt(a: var array[8, uint8], f: var float64) = assert sizeof(a) == sizeof(f) copyMem(addr f, addr a[0], sizeof f) Run
Re: Convert float to its corresponding bytes?
afaik atleast in C there's no "safe" way to do it. The method presented by @e works in most situations, but breaks strict aliasing (a poiner of one type may not be casted to a pointer of an incompatible type). The usual safer way, in C is by using a union: type Uint8ToFloat64 {.union.} = object f: float64 i: array[8, uint8] proc floatToInts(f: float64): array[8, uint8] = var convert: Uint8ToFloat64 convert.f = f convert.i proc intsToFloat(i: array[8, uint8]): float64 = var convert: Uint8ToFloat64 convert.i = i convert.f doAssert intsToFloat(floatToInts(-42.0)) == -42.0 Run
Re: Convert float to its corresponding bytes?
Thank you very much, this is exactly what I need. I was thinking about using casts but wasn't really sure if it's safe.
Re: Convert float to its corresponding bytes?
Here's a little program demonstrating conversion functions: import parseutils, os func flt2arr (x: float64) : array[0..7, uint8] = result = cast[array[0..7, uint8]](x) func arr2flt (a: array[0..7, uint8]) : float64 = result = cast[float64](a) when isMainModule: let params = commandLineParams() var flt : float64 discard parseFloat(params[0], flt) let ary = flt2arr(flt) for u in ary: echo(u) let arr : array[0..7, uint8] = [ary[0]+1, ary[1], ary[2], ary[3], ary[4], ary[5], ary[6], ary[7]] echo(arr2flt(arr)) Run