doubledouble atan2(const doubledouble& qy, const doubledouble& qx) { // Based on GNU libc atan2.c static const double one=1.0, zero=0.0; double x, y; x=qx.h(); y=qy.h(); double signx, signy; if (x!=x) return qx; // x=NaN if (y!=y) return qy; #ifndef WIN32 signy=copysign(one,y); signx=copysign(one,x); #else signy=_copysign(one,y); signx=_copysign(one,x); #endif if (y==zero) return signx==one ? qy : Qcopysign(doubledouble::Pi,signy); if (x==zero) return Qcopysign(doubledouble::Pion2,signy); // Dustin Graves 2002Apr06 #ifndef WIN32 if (DD_ISINF(x)) { if (DD_ISINF(y)) return Qcopysign(signx==one ? doubledouble::Pion4 : 3.0*doubledouble::Pion4,signy); else return Qcopysign(signx==one ? doubledouble(0.0) : doubledouble::Pi,signy); } if (DD_ISINF(y)) return Qcopysign(doubledouble::Pion2,signy); //#else // if (_isnan(x)) { // if (_isnan(y)) return Qcopysign(signx==one ? doubledouble::Pion4 : 3.0*doubledouble::Pion4,signy); // else return Qcopysign(signx==one ? doubledouble(0.0) : doubledouble::Pi,signy); // } // if (_isnan(y)) return Qcopysign(doubledouble::Pion2,signy); //#endif doubledouble aqy=fabs(qy); if (x<0.0) // X is negative. return Qcopysign(doubledouble::Pi-atan(aqy/(-qx)),signy); return Qcopysign(atan(aqy/qx),signy); }
int get_double_expn(double x) { int i = 0; double y; if (x == 0.0) { return INT_MIN; } if (DD_ISINF(x) || DD_ISNAN(x)) { return INT_MAX; } y = fabs(x); if (y < 1.0) { while (y < 1.0) { y *= 2.0; i++; } return -i; } else if (y >= 2.0) { while (y >= 2.0) { y *= 0.5; i++; } return i; } return 0; }