KnowledgeHub
Questions
Tags
Users
Search
Alex Rivera
|
Logout
Edit Question
Title
Body
I browsed through the recently released Doom 3 BFG source code , when I came upon something that does not appear to make any sense. Doom 3 wraps mathematical functions in the idMath class. Some of the functions just foward to the corresponding functions from math.h , but some are reimplementations (e.g. idMath::exp16() ) that I assume have a higher performance than their math.h counterparts (maybe at the expense of precision). What baffles me, however, is the way they have implemented the float idMath::Sqrt(float x) function: ID_INLINE float idMath::InvSqrt( float x ) { return ( x > FLT_SMALLEST_NON_DENORMAL ) ? sqrtf( 1.0f / x ) : INFINITY; } ID_INLINE float idMath::Sqrt( float x ) { return ( x >= 0.0f ) ? x * InvSqrt( x ) : 0.0f; } This appears to perform two unnecessary floating point operations: First a division and then a multiplication. It is interesting to note that the original Doom 3 source code also implemented the square root function in this way, but the inverse square root uses the fast inverse square root algorithm . ID_INLINE float idMath::InvSqrt( float x ) { dword a = ((union _flint*)(&x))->i; union _flint seed; assert( initialized ); double y = x * 0.5f; seed.i = (( ( (3*EXP_BIAS-1) - ( (a >> EXP_POS) & 0xFF) ) >> 1)<<EXP_POS) | iSqrt[(a >> (EXP_POS-LOOKUP_BITS)) & LOOKUP_MASK]; double r = seed.f; r = r * ( 1.5f - r * r * y ); r = r * ( 1.5f - r * r * y ); return (float) r; } ID_INLINE float
Tags (comma-separated)
Save Edits
Cancel