Warning, file /include/vdt/atan.h was not indexed
or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027 #ifndef ATAN_H_
0028 #define ATAN_H_
0029
0030 #include "vdtcore_common.h"
0031
0032 namespace vdt{
0033
0034 namespace details{
0035 const double T3PO8 = 2.41421356237309504880;
0036 const double MOREBITSO2 = MOREBITS * 0.5;
0037
0038 inline double get_atan_px(const double x2){
0039
0040 const double PX1atan = -8.750608600031904122785E-1;
0041 const double PX2atan = -1.615753718733365076637E1;
0042 const double PX3atan = -7.500855792314704667340E1;
0043 const double PX4atan = -1.228866684490136173410E2;
0044 const double PX5atan = -6.485021904942025371773E1;
0045
0046 double px = PX1atan;
0047 px *= x2;
0048 px += PX2atan;
0049 px *= x2;
0050 px += PX3atan;
0051 px *= x2;
0052 px += PX4atan;
0053 px *= x2;
0054 px += PX5atan;
0055
0056 return px;
0057 }
0058
0059
0060 inline double get_atan_qx(const double x2){
0061 const double QX1atan = 2.485846490142306297962E1;
0062 const double QX2atan = 1.650270098316988542046E2;
0063 const double QX3atan = 4.328810604912902668951E2;
0064 const double QX4atan = 4.853903996359136964868E2;
0065 const double QX5atan = 1.945506571482613964425E2;
0066
0067 double qx=x2;
0068 qx += QX1atan;
0069 qx *=x2;
0070 qx += QX2atan;
0071 qx *=x2;
0072 qx += QX3atan;
0073 qx *=x2;
0074 qx += QX4atan;
0075 qx *=x2;
0076 qx += QX5atan;
0077
0078 return qx;
0079 }
0080
0081 }
0082
0083
0084
0085
0086 inline double fast_atan(double x){
0087
0088
0089 const uint64_t sign_mask = details::getSignMask(x);
0090 x=std::fabs(x);
0091
0092
0093 const double originalx=x;
0094
0095 double y = details::PIO4;
0096 double factor = details::MOREBITSO2;
0097 x = (x-1.0) / (x+1.0);
0098
0099 if( originalx > details::T3PO8 ) {
0100 y = details::PIO2;
0101 factor = details::MOREBITS;
0102 x = -1.0 / originalx ;
0103 }
0104 if ( originalx <= 0.66 ) {
0105 y = 0.;
0106 factor = 0.;
0107 x = originalx;
0108 }
0109
0110 const double x2 = x * x;
0111
0112 const double px = details::get_atan_px(x2);
0113 const double qx = details::get_atan_qx(x2);
0114
0115
0116
0117 const double poq=px / qx;
0118
0119 double res = x * x2 * poq + x;
0120 res+=y;
0121
0122 res+=factor;
0123
0124 return details::dpORuint64(res,sign_mask);
0125 }
0126
0127
0128
0129 inline float fast_atanf( float xx ) {
0130
0131 const uint32_t sign_mask = details::getSignMask(xx);
0132
0133 float x= std::fabs(xx);
0134 const float x0=x;
0135 float y=0.0f;
0136
0137
0138 if( x0 > 0.4142135623730950f ){
0139 x = (x0-1.0f)/(x0+1.0f);
0140 y = details::PIO4F;
0141 }
0142 if( x0 > 2.414213562373095f ){
0143 x = -( 1.0f/x0 );
0144 y = details::PIO2F;
0145 }
0146
0147
0148 const float x2 = x * x;
0149 y +=
0150 ((( 8.05374449538e-2f * x2
0151 - 1.38776856032E-1f) * x2
0152 + 1.99777106478E-1f) * x2
0153 - 3.33329491539E-1f) * x2 * x
0154 + x;
0155
0156 return details::spORuint32(y,sign_mask);
0157 }
0158
0159
0160
0161
0162 void atanv(const uint32_t size, double const * __restrict__ iarray, double* __restrict__ oarray);
0163 void fast_atanv(const uint32_t size, double const * __restrict__ iarray, double* __restrict__ oarray);
0164 void atanfv(const uint32_t size, float const * __restrict__ iarray, float* __restrict__ oarray);
0165 void fast_atanfv(const uint32_t size, float const * __restrict__ iarray, float* __restrict__ oarray);
0166
0167 }
0168
0169 #endif