Mercurial > hg > octave-lyh
changeset 10414:2a8b1db1e2ca
implement built-in cbrt
author | Jaroslav Hajek <highegg@gmail.com> |
---|---|
date | Tue, 16 Mar 2010 15:16:32 +0100 |
parents | 271c5262975b |
children | 976e76b77fa0 |
files | configure.ac liboctave/ChangeLog liboctave/lo-specfun.cc liboctave/lo-specfun.h src/ChangeLog src/mappers.cc src/ov-base.cc src/ov-base.h src/ov-float.cc src/ov-flt-re-mat.cc src/ov-re-mat.cc src/ov-re-sparse.cc src/ov-scalar.cc src/ov.h |
diffstat | 14 files changed, 94 insertions(+), 1 deletions(-) [+] |
line wrap: on
line diff
--- a/configure.ac +++ b/configure.ac @@ -1690,7 +1690,7 @@ ### Check for nonstandard but common math functions that we need. AC_CHECK_FUNCS(acosh acoshf asinh asinhf atanh atanhf erf erff erfc erfcf exp2f log2 log2f) -AC_CHECK_FUNCS(hypotf _hypotf) +AC_CHECK_FUNCS(hypotf _hypotf cbrt cbrtf) ### Checks for OS specific cruft.
--- a/liboctave/ChangeLog +++ b/liboctave/ChangeLog @@ -1,3 +1,9 @@ +2010-03-16 Jaroslav Hajek <highegg@gmail.com> + + * lo-specfun.cc: Substitute cbrt and cbrtf if needed. + * lo-specfun.h: Declare cbrt and cbrtf if needed. + * configure.ac: Check for cbrt and cbrtf. + 2010-03-15 John W. Eaton <jwe@octave.org> * oct-glob.cc (octave_glob): Tag calls to glob and globfree with
--- a/liboctave/lo-specfun.cc +++ b/liboctave/lo-specfun.cc @@ -560,6 +560,22 @@ return retval; } +#if !defined (HAVE_CBRT) +double cbrt (double x) +{ + static const double one_third = 0.3333333333333333333; + if (xfinite (x)) + { + // Use pow. + double y = std::pow (std::abs (x), one_third) * signum (x); + // Correct for better accuracy. + return (x / (y*y) + y + y) / 3; + } + else + return x; +} +#endif + #if !defined (HAVE_LOG1PF) float log1pf (float x) @@ -603,6 +619,22 @@ return retval; } +#if !defined (HAVE_CBRTF) +float cbrtf (float x) +{ + static const float one_third = 0.3333333333333333333f; + if (xfinite (x)) + { + // Use pow. + float y = std::pow (std::abs (x), one_third) * signum (x); + // Correct for better accuracy. + return (x / (y*y) + y + y) / 3; + } + else + return x; +} +#endif + static inline Complex zbesj (const Complex& z, double alpha, int kode, octave_idx_type& ierr);
--- a/liboctave/lo-specfun.h +++ b/liboctave/lo-specfun.h @@ -101,6 +101,14 @@ #endif extern OCTAVE_API FloatComplex log1p (const FloatComplex& x); +#if !defined (HAVE_CBRT) +extern OCTAVE_API double cbrt (double x); +#endif + +#if !defined (HAVE_CBRTF) +extern OCTAVE_API float cbrtf (float x); +#endif + extern OCTAVE_API double xgamma (double x); extern OCTAVE_API double xlgamma (double x); extern OCTAVE_API Complex rc_lgamma (double x);
--- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,13 @@ +2010-03-16 Jaroslav Hajek <highegg@gmail.com> + + * ov-base.h (unary_mapper_t::umap_cbrt): New enum member. + * ov.h (octave_value::cbrt): New forwarder method. + * ov-scalar.cc (octave_scalar::map): Handle cbrt. + * ov-float.cc (octave_float_scalar::map): Ditto. + * ov-re-mat.cc (octave_matrix::map): Ditto. + * ov-flt-re-mat.cc (octave_float_matrix::map): Ditto. + * ov-re-sparse.cc (octave_sparse_matrix::map): Ditto. + 2010-03-15 John W. Eaton <jwe@octave.org> * oct-parse.yy, lex.ll: Undefine GNULIB_NAMESPACE immediately
--- a/src/mappers.cc +++ b/src/mappers.cc @@ -351,6 +351,35 @@ */ +DEFUN (cbrt, args, , + "-*- texinfo -*-\n\ +@deftypefn {Mapping Function} {} cbrt (@var{x})\n\ +Return the real cube root of @var{x}. Unlike @code{@var{x}^(1/3)},\n\ +the result will be negative if @var{x} is negative.\n\ +@end deftypefn") +{ + octave_value retval; + if (args.length () == 1) + retval = args(0).cbrt (); + else + print_usage (); + + return retval; +} + +/* + +%!assert (cbrt (64), 4) +%!assert (cbrt (-125), -5) +%!assert (cbrt (0), 0) +%!assert (cbrt (Inf), Inf) +%!assert (cbrt (-Inf), -Inf) +%!assert (cbrt (NaN), NaN) +%!assert (cbrt (2^300), 2^100) +%!assert (cbrt (125*2^300), 5*2^100) + +*/ + DEFUN (ceil, args, , "-*- texinfo -*-\n\ @deftypefn {Mapping Function} {} ceil (@var{x})\n\
--- a/src/ov-base.cc +++ b/src/ov-base.cc @@ -1150,6 +1150,7 @@ "asinh", "atan", "atanh", + "cbrt", "ceil", "conj", "cos",
--- a/src/ov-base.h +++ b/src/ov-base.h @@ -658,6 +658,7 @@ umap_asinh, umap_atan, umap_atanh, + umap_cbrt, umap_ceil, umap_conj, umap_cos,
--- a/src/ov-float.cc +++ b/src/ov-float.cc @@ -290,6 +290,7 @@ SCALAR_MAPPER (erfcx, ::erfcx); SCALAR_MAPPER (gamma, xgamma); SCALAR_MAPPER (lgamma, rc_lgamma); + SCALAR_MAPPER (cbrt, ::cbrtf); SCALAR_MAPPER (ceil, ::ceilf); SCALAR_MAPPER (cos, ::cosf); SCALAR_MAPPER (cosh, ::coshf);
--- a/src/ov-flt-re-mat.cc +++ b/src/ov-flt-re-mat.cc @@ -770,6 +770,7 @@ ARRAY_MAPPER (erfcx, float, ::erfcx); ARRAY_MAPPER (gamma, float, xgamma); RC_ARRAY_MAPPER (lgamma, FloatComplex, rc_lgamma); + ARRAY_MAPPER (cbrt, float, ::cbrtf); ARRAY_MAPPER (ceil, float, ::ceilf); ARRAY_MAPPER (cos, float, ::cosf); ARRAY_MAPPER (cosh, float, ::coshf);
--- a/src/ov-re-mat.cc +++ b/src/ov-re-mat.cc @@ -893,6 +893,7 @@ ARRAY_MAPPER (erfcx, double, ::erfcx); ARRAY_MAPPER (gamma, double, xgamma); RC_ARRAY_MAPPER (lgamma, Complex, rc_lgamma); + ARRAY_MAPPER (cbrt, double, ::cbrt); ARRAY_MAPPER (ceil, double, ::ceil); ARRAY_MAPPER (cos, double, ::cos); ARRAY_MAPPER (cosh, double, ::cosh);
--- a/src/ov-re-sparse.cc +++ b/src/ov-re-sparse.cc @@ -913,6 +913,7 @@ ARRAY_MAPPER (erfc, double, ::erfc); ARRAY_MAPPER (gamma, double, xgamma); ARRAY_MAPPER (lgamma, Complex, rc_lgamma); + ARRAY_MAPPER (cbrt, double, ::cbrt); ARRAY_MAPPER (ceil, double, ::ceil); ARRAY_MAPPER (cos, double, ::cos); ARRAY_MAPPER (cosh, double, ::cosh);