Earlier quoted context omitted.
That's the Linux way to do it union { int i; float f } u { .f = 1.23f }; int i = u.i; Another way is a memcpy, which I believe is the most defined way to do type punning int i; float f; memcpy(&i, &f, 4); But you also have to assume the size of those primitive types but that's pretty safe in modern C/C++.
In C++, type punning through pointers and unions is undefined behavior. Even `reinterpret_cast ` isn’t allowed because of aliasing (IIRC). The only “defined” way to do type punning is a memcpy. A compiler targeting something like x86 would optimize out the memcpy. For more information, see the C++20 final draft[0§7.6.1.9] [0]: https://isocpp.org/files/papers/N4860.pdf
Fast Inverse Square Root
31–40 of 100 posts
Re: Fast Inverse Square Root
#32To me "inverse square root" means "square" so it makes the title of this kind of funny.
Re: Fast Inverse Square Root
#33Earlier quoted context omitted.
Thanks for this. I have one nit. You show `q = 1598029824 - u/2;` as being identical to `q = 0x5F400000 - u >> 1;`, but every language I know of uses a different order of operations, giving different results. It might be clearest to provide parentheses in the second case.
Interestingly enough it seems to do the shift first in Swift
Re: Fast Inverse Square Root
#34Earlier quoted context omitted.
That's the Linux way to do it union { int i; float f } u { .f = 1.23f }; int i = u.i; Another way is a memcpy, which I believe is the most defined way to do type punning int i; float f; memcpy(&i, &f, 4); But you also have to assume the size of those primitive types but that's pretty safe in modern C/C++.
In C++, type punning through pointers and unions is undefined behavior. Even `reinterpret_cast ` isn’t allowed because of aliasing (IIRC). The only “defined” way to do type punning is a memcpy. A compiler targeting something like x86 would optimize out the memcpy. For more information, see the C++20 final draft[0§7.6.1.9] [0]: https://isocpp.org/files/papers/N4860.pdf
Re: Fast Inverse Square Root
#35Earlier quoted context omitted.
Would a union do the trick?
That's the Linux way to do it union { int i; float f } u { .f = 1.23f }; int i = u.i; Another way is a memcpy, which I believe is the most defined way to do type punning int i; float f; memcpy(&i, &f, 4); But you also have to assume the size of those primitive types but that's pretty safe in modern C/C++.
https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html#Typ...
> you also have to assume the size of those primitive types
This usually works though there's some situations where you could still be surprised. For instance if you're programming embedded processors with avr-gcc you'll have sizeof(double)==4
Re: Fast Inverse Square Root
#36This is an explanation of the fast inverse square root that I hope is easy to understand. I also managed to improve on it a little bit.
Thanks for this. I have one nit. You show `q = 1598029824 - u/2;` as being identical to `q = 0x5F400000 - u >> 1;`, but every language I know of uses a different order of operations, giving different results. It might be clearest to provide parentheses in the second case.
Re: Fast Inverse Square Root
#37Earlier quoted context omitted.
Interestingly enough it seems to do the shift first in Swift
All well-known programming languages will do the shift first.
I think I'm missing a reference/joke =/
Re: Fast Inverse Square Root
#38If only 1% of cpu time was spent on slow square root, and this sped it up by 100%, it would be barely worth it.
Re: Fast Inverse Square Root
#39What was the speedup from this? If only 1% of cpu time was spent on slow square root, and this sped it up by 100%, it would be barely worth it.
Also, a "mere" 1% speedup seems trivial for most general coding but squeezing 1% out of optimized game code is like blood from a stone. Add a bunch of similar tricks together and you can see 10-20% overall improvement which is huge.
Re: Fast Inverse Square Root
#40What was the speedup from this? If only 1% of cpu time was spent on slow square root, and this sped it up by 100%, it would be barely worth it.