cbrt.c 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. /* cbrt.c
  2. *
  3. * Cube root
  4. *
  5. *
  6. *
  7. * SYNOPSIS:
  8. *
  9. * double x, y, cbrt();
  10. *
  11. * y = cbrt( x );
  12. *
  13. *
  14. *
  15. * DESCRIPTION:
  16. *
  17. * Returns the cube root of the argument, which may be negative.
  18. *
  19. * Range reduction involves determining the power of 2 of
  20. * the argument. A polynomial of degree 2 applied to the
  21. * mantissa, and multiplication by the cube root of 1, 2, or 4
  22. * approximates the root to within about 0.1%. Then Newton's
  23. * iteration is used three times to converge to an accurate
  24. * result.
  25. *
  26. *
  27. *
  28. * ACCURACY:
  29. *
  30. * Relative error:
  31. * arithmetic domain # trials peak rms
  32. * DEC -10,10 200000 1.8e-17 6.2e-18
  33. * IEEE 0,1e308 30000 1.5e-16 5.0e-17
  34. *
  35. */
  36. /* cbrt.c */
  37. /*
  38. Cephes Math Library Release 2.8: June, 2000
  39. Copyright 1984, 1991, 2000 by Stephen L. Moshier
  40. */
  41. #include <math.h>
  42. static double CBRT2 = 1.2599210498948731647672;
  43. static double CBRT4 = 1.5874010519681994747517;
  44. static double CBRT2I = 0.79370052598409973737585;
  45. static double CBRT4I = 0.62996052494743658238361;
  46. #ifdef ANSIPROT
  47. extern double frexp ( double, int * );
  48. extern double ldexp ( double, int );
  49. extern int isnan ( double );
  50. extern int isfinite ( double );
  51. #else
  52. double frexp(), ldexp();
  53. int isnan(), isfinite();
  54. #endif
  55. double cbrt(x)
  56. double x;
  57. {
  58. int e, rem, sign;
  59. double z;
  60. #ifdef NANS
  61. if( isnan(x) )
  62. return x;
  63. #endif
  64. #ifdef INFINITIES
  65. if( !isfinite(x) )
  66. return x;
  67. #endif
  68. if( x == 0 )
  69. return( x );
  70. if( x > 0 )
  71. sign = 1;
  72. else
  73. {
  74. sign = -1;
  75. x = -x;
  76. }
  77. z = x;
  78. /* extract power of 2, leaving
  79. * mantissa between 0.5 and 1
  80. */
  81. x = frexp( x, &e );
  82. /* Approximate cube root of number between .5 and 1,
  83. * peak relative error = 9.2e-6
  84. */
  85. x = (((-1.3466110473359520655053e-1 * x
  86. + 5.4664601366395524503440e-1) * x
  87. - 9.5438224771509446525043e-1) * x
  88. + 1.1399983354717293273738e0 ) * x
  89. + 4.0238979564544752126924e-1;
  90. /* exponent divided by 3 */
  91. if( e >= 0 )
  92. {
  93. rem = e;
  94. e /= 3;
  95. rem -= 3*e;
  96. if( rem == 1 )
  97. x *= CBRT2;
  98. else if( rem == 2 )
  99. x *= CBRT4;
  100. }
  101. /* argument less than 1 */
  102. else
  103. {
  104. e = -e;
  105. rem = e;
  106. e /= 3;
  107. rem -= 3*e;
  108. if( rem == 1 )
  109. x *= CBRT2I;
  110. else if( rem == 2 )
  111. x *= CBRT4I;
  112. e = -e;
  113. }
  114. /* multiply by power of 2 */
  115. x = ldexp( x, e );
  116. /* Newton iteration */
  117. x -= ( x - (z/(x*x)) )*0.33333333333333333333;
  118. #ifdef DEC
  119. x -= ( x - (z/(x*x)) )/3.0;
  120. #else
  121. x -= ( x - (z/(x*x)) )*0.33333333333333333333;
  122. #endif
  123. if( sign < 0 )
  124. x = -x;
  125. return(x);
  126. }