示例#1
0
static void
special_overflow (void)
{
  /* Check for overflow in 3 cases:
     1. cosh(x) is representable, but not exp(x)
     2. cosh(x) is not representable in the selected range of exp.
     3. cosh(x) exp overflow even with the largest range of exp */
  mpfr_t x, y;
  mp_exp_t emin, emax;

  emin = mpfr_get_emin ();
  emax = mpfr_get_emax ();

  set_emin (-125);
  set_emax (128);

  mpfr_init2 (x, 24);
  mpfr_init2 (y, 24);

  mpfr_set_str_binary (x, "0.101100100000000000110100E7");
  mpfr_cosh (y, x, GMP_RNDN);
  if (mpfr_cmp_str (y, "0.101010001111001010001110E128", 2, GMP_RNDN))
    {
      printf("Special overflow error 1.\n");
      mpfr_dump (y);
      exit (1);
    }

  mpfr_set_str_binary (x, "0.101100100000000000110100E8");
  mpfr_cosh (y, x, GMP_RNDN);
  if (!mpfr_inf_p(y))
    {
      printf("Special overflow error 2.\n");
      mpfr_dump (y);
      exit (1);
    }

  set_emin (emin);
  set_emax (emax);

  mpfr_set_str_binary (x, "0.101100100000000000110100E1000000");
  mpfr_cosh (y, x, GMP_RNDN);
  if (!mpfr_inf_p(y))
    {
      printf("Special overflow error 3.\n");
      mpfr_dump (y);
      exit (1);
    }

  mpfr_clear (y);
  mpfr_clear (x);
}
示例#2
0
文件: rpn-trig.cpp 项目: louis-/rpn
/// @brief sin keyword implementation
///
void program::rpn_sin(void) {
    MIN_ARGUMENTS(1);

    if (_stack->get_type(0) == cmd_number) {
        floating_t* left = &((number*)_stack->get_obj(0))->_value;
        CHECK_MPFR(mpfr_sin(left->mpfr, left->mpfr, floating_t::s_mpfr_rnd));
    } else if (_stack->get_type(0) == cmd_complex) {
        // sin(x+iy)=sin(x)cosh(y)+icos(x)sinh(y)
        stack::copy_and_push_back(*_stack, _stack->size() - 1, _calc_stack);

        floating_t* tmp = &((number*)_calc_stack.allocate_back(number::calc_size(), cmd_number))->_value;
        floating_t* x = ((complex*)_calc_stack.get_obj(1))->re();
        floating_t* y = ((complex*)_calc_stack.get_obj(1))->im();

        floating_t* re = ((complex*)_stack->get_obj(0))->re();
        floating_t* im = ((complex*)_stack->get_obj(0))->im();

        CHECK_MPFR(mpfr_sin(re->mpfr, x->mpfr, floating_t::s_mpfr_rnd));
        CHECK_MPFR(mpfr_cosh(tmp->mpfr, y->mpfr, floating_t::s_mpfr_rnd));
        CHECK_MPFR(mpfr_mul(re->mpfr, re->mpfr, tmp->mpfr, floating_t::s_mpfr_rnd));

        CHECK_MPFR(mpfr_cos(im->mpfr, x->mpfr, floating_t::s_mpfr_rnd));
        CHECK_MPFR(mpfr_sinh(tmp->mpfr, y->mpfr, floating_t::s_mpfr_rnd));
        CHECK_MPFR(mpfr_mul(im->mpfr, im->mpfr, tmp->mpfr, floating_t::s_mpfr_rnd));

        _calc_stack.pop_back(2);
    } else
        ERR_CONTEXT(ret_bad_operand_type);
}
示例#3
0
文件: t-cosh.c 项目: argriffing/arb
int main()
{
    slong iter;
    flint_rand_t state;

    flint_printf("cosh....");
    fflush(stdout);

    flint_randinit(state);

    for (iter = 0; iter < 100000 * arb_test_multiplier(); iter++)
    {
        arb_t a, b;
        fmpq_t q;
        mpfr_t t;
        slong prec = 2 + n_randint(state, 200);

        arb_init(a);
        arb_init(b);
        fmpq_init(q);
        mpfr_init2(t, prec + 100);

        arb_randtest(a, state, 1 + n_randint(state, 200), 3);
        arb_randtest(b, state, 1 + n_randint(state, 200), 3);
        arb_get_rand_fmpq(q, state, a, 1 + n_randint(state, 200));

        fmpq_get_mpfr(t, q, MPFR_RNDN);
        mpfr_cosh(t, t, MPFR_RNDN);

        arb_cosh(b, a, prec);

        if (!arb_contains_mpfr(b, t))
        {
            flint_printf("FAIL: containment\n\n");
            flint_printf("a = "); arb_print(a); flint_printf("\n\n");
            flint_printf("b = "); arb_print(b); flint_printf("\n\n");
            abort();
        }

        arb_cosh(a, a, prec);

        if (!arb_equal(a, b))
        {
            flint_printf("FAIL: aliasing\n\n");
            abort();
        }

        arb_clear(a);
        arb_clear(b);
        fmpq_clear(q);
        mpfr_clear(t);
    }

    flint_randclear(state);
    flint_cleanup();
    flint_printf("PASS\n");
    return EXIT_SUCCESS;
}
示例#4
0
decimal r_cosh(const decimal& a,bool round)
{
#ifdef USE_CGAL
	CGAL::Gmpfr m;
	CGAL::Gmpfr n=to_gmpfr(a);
	mpfr_cosh(m.fr(),n.fr(),MPFR_RNDN);
	return r_round_preference(decimal(m),round);
#else
	return r_round_preference(cosh(a),round);
#endif
}
示例#5
0
//------------------------------------------------------------------------------
// Name:
//------------------------------------------------------------------------------
knumber_base *knumber_float::cosh() {
#ifdef KNUMBER_USE_MPFR
	mpfr_t mpfr;
	mpfr_init_set_f(mpfr, mpf_, rounding_mode);
	mpfr_cosh(mpfr, mpfr, rounding_mode);
	mpfr_get_f(mpf_, mpfr, rounding_mode);
	mpfr_clear(mpfr);
	return this;
#else
	const double x = mpf_get_d(mpf_);
	return execute_libc_func< ::cosh>(x);
#endif
}
static void
pure_real_argument (void)
{
  /* cosh(x -i*0) = cosh(x) +i*0 if x<0 */
  /* cosh(x -i*0) = cosh(x) -i*0 if x>0 */
  /* cosh(x +i*0) = cosh(x) -i*0 if x<0 */
  /* cosh(x -i*0) = cosh(x) +i*0 if x>0 */
  mpc_t u;
  mpc_t z;
  mpc_t cosh_z;

  mpc_init2 (z, 2);
  mpc_init2 (u, 100);
  mpc_init2 (cosh_z, 100);

  /* cosh(1 +i*0) = cosh(1) +i*0 */
  mpc_set_ui_ui (z, 1, 0, MPC_RNDNN);
  mpfr_cosh (MPC_RE (u), MPC_RE (z), GMP_RNDN);
  mpfr_set_ui (MPC_IM (u), 0, GMP_RNDN);
  mpc_cosh (cosh_z, z, MPC_RNDNN);
  if (mpc_cmp (cosh_z, u) != 0 || mpfr_signbit (MPC_IM (cosh_z)))
    TEST_FAILED ("mpc_cosh", z, cosh_z, u, MPC_RNDNN);

  /* cosh(1 -i*0) = cosh(1) -i*0 */
  mpc_conj (z, z, MPC_RNDNN);
  mpc_conj (u, u, MPC_RNDNN);
  mpc_cosh (cosh_z, z, MPC_RNDNN);
  if (mpc_cmp (cosh_z, u) != 0 || !mpfr_signbit (MPC_IM (cosh_z)))
    TEST_FAILED ("mpc_cosh", z, cosh_z, u, MPC_RNDNN);

  /* cosh(-1 +i*0) = cosh(1) -i*0 */
  mpc_neg (z, z, MPC_RNDNN);
  mpc_cosh (cosh_z, z, MPC_RNDNN);
  if (mpc_cmp (cosh_z, u) != 0 || !mpfr_signbit (MPC_IM (cosh_z)))
    TEST_FAILED ("mpc_cosh", z, cosh_z, u, MPC_RNDNN);

  /* cosh(-1 -i*0) = cosh(1) +i*0 */
  mpc_conj (z, z, MPC_RNDNN);
  mpc_conj (u, u, MPC_RNDNN);
  mpc_cosh (cosh_z, z, MPC_RNDNN);
  if (mpc_cmp (cosh_z, u) != 0 || mpfr_signbit (MPC_IM (cosh_z)))
    TEST_FAILED ("mpc_cosh", z, cosh_z, u, MPC_RNDNN);

  mpc_clear (cosh_z);
  mpc_clear (z);
  mpc_clear (u);
}
示例#7
0
文件: tsinh_cosh.c 项目: Canar/mpfr
/* check against sinh, cosh */
static void
check (mpfr_t x, mpfr_rnd_t rnd)
{
  mpfr_t s, c, sx, cx;
  int isc, is, ic;

  mpfr_inits2 (MPFR_PREC(x), s, c, sx, cx, (mpfr_ptr) 0);

  isc = mpfr_sinh_cosh (sx, cx, x, rnd);
  is = mpfr_sinh (s, x, rnd);
  ic = mpfr_cosh (c, x, rnd);

  if (!mpfr_equal_p (s, sx) || !mpfr_equal_p (c, cx))
    failed (x, s, sx, c, cx);
  MPFR_ASSERTN (isc = is || ic);

  mpfr_clears (s, c, sx, cx, (mpfr_ptr) 0);
}
static int
mpc_sin_cos_imag (mpc_ptr rop_sin, mpc_ptr rop_cos, mpc_srcptr op,
   mpc_rnd_t rnd_sin, mpc_rnd_t rnd_cos)
   /* assumes that op is purely imaginary */
{
   int inex_sin_im = 0, inex_cos_re = 0;
      /* assume exact if not computed */
   int overlap;
   mpc_t op_loc;

   overlap = (rop_sin == op || rop_cos == op);
   if (overlap) {
      mpc_init3 (op_loc, MPC_PREC_RE (op), MPC_PREC_IM (op));
      mpc_set (op_loc, op, MPC_RNDNN);
   }
   else
      op_loc [0] = op [0];

   if (rop_sin != NULL) {
      /* sin(+-O +i*y) = +-0 +i*sinh(y) */
      mpfr_set (MPC_RE(rop_sin), MPC_RE(op_loc), GMP_RNDN);
      inex_sin_im = mpfr_sinh (MPC_IM(rop_sin), MPC_IM(op_loc), MPC_RND_IM(rnd_sin));
   }

   if (rop_cos != NULL) {
      /* cos(-0 - i * y) = cos(+0 + i * y) = cosh(y) - i * 0,
         cos(-0 + i * y) = cos(+0 - i * y) = cosh(y) + i * 0,
         where y >= 0 */

      if (mpfr_zero_p (MPC_IM (op_loc)))
        inex_cos_re = mpfr_set_ui (MPC_RE (rop_cos), 1ul, MPC_RND_RE (rnd_cos));
      else
        inex_cos_re = mpfr_cosh (MPC_RE (rop_cos), MPC_IM (op_loc), MPC_RND_RE (rnd_cos));

      mpfr_set_ui (MPC_IM (rop_cos), 0ul, MPC_RND_IM (rnd_cos));
      if (mpfr_signbit (MPC_RE (op_loc)) ==  mpfr_signbit (MPC_IM (op_loc)))
         MPFR_CHANGE_SIGN (MPC_IM (rop_cos));
   }

   if (overlap)
      mpc_clear (op_loc);

   return MPC_INEX12 (MPC_INEX (0, inex_sin_im), MPC_INEX (inex_cos_re, 0));
}
示例#9
0
文件: thyperbolic.c 项目: Canar/mpfr
static int
check_NAN (void)
{
  mpfr_t t, ch,sh,th,ach,ash,ath;
  int tester;
  int fail = 0;

  mpfr_init2(t,200);
  mpfr_init2(ch,200);
  mpfr_init2(sh,200);
  mpfr_init2(th,200);
  mpfr_init2(ach,200);
  mpfr_init2(ash,200);
  mpfr_init2(ath,200);

  MPFR_SET_NAN(t);

  /******cosh********/

  tester=mpfr_cosh(ch,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ch) || tester!=0)
    {
      printf("cosh NAN \n");
      fail = 1;
      goto clean_up;
    }

  /******sinh********/

  tester=mpfr_sinh(sh,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(sh) || tester!=0)
    {
      printf("sinh NAN \n");
      fail = 1;
      goto clean_up;
    }

  /******tanh********/

  tester=mpfr_tanh(th,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(th) || tester!=0)
    {
      printf("tanh NAN \n");
      fail = 1;
      goto clean_up;
    }

  /******acosh********/

  tester=mpfr_acosh(ach,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ach) || tester!=0)
    {
      printf("acosh NAN \n");
      fail = 1;
      goto clean_up;
    }

  /******asinh********/

  tester=mpfr_asinh(ash,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ash) || tester!=0)
    {
      printf("asinh NAN \n");
      fail = 1;
      goto clean_up;
    }

  /******atanh********/

  tester=mpfr_atanh(ath,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ath) || tester!=0)
    {
      printf("atanh NAN \n");
      fail = 1;
      goto clean_up;
    }

 clean_up:
  mpfr_clear(t);
  mpfr_clear(ch);
  mpfr_clear(sh);
  mpfr_clear(th);
  mpfr_clear(ach);
  mpfr_clear(ash);
  mpfr_clear(ath);

  return fail;
}
示例#10
0
文件: thyperbolic.c 项目: Canar/mpfr
static int
check_INF (void)
{
  mpfr_t t, ch, sh, th, ach, ash, ath;
  int tester;
  int fail = 0;

  mpfr_init2 (t, 200);
  mpfr_init2 (ch, 200);
  mpfr_init2 (sh, 200);
  mpfr_init2 (th, 200);
  mpfr_init2 (ach, 200);
  mpfr_init2 (ash, 200);
  mpfr_init2 (ath, 200);

  MPFR_SET_INF(t);

  if(MPFR_IS_NEG (t))
    MPFR_CHANGE_SIGN(t);

  /******cosh********/

  tester = mpfr_cosh(ch,t,MPFR_RNDD);
  if (!MPFR_IS_INF(ch) || MPFR_IS_NEG (ch) || tester!=0)
    {
      printf("cosh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******sinh********/

  tester=mpfr_sinh(sh,t,MPFR_RNDD);
  if (!MPFR_IS_INF(sh) || MPFR_IS_NEG (sh)  || tester!=0)
    {
      printf("sinh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******tanh********/

  tester=mpfr_tanh(th,t,MPFR_RNDD);
  if (mpfr_cmp_ui(th,1) != 0 || tester!=0)
    {
      printf("tanh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******acosh********/

  tester=mpfr_acosh(ach,t,MPFR_RNDD);
  if (!MPFR_IS_INF(ach) || MPFR_IS_NEG (ach)  || tester!=0)
    {
      printf("acosh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******asinh********/

  tester=mpfr_asinh(ash,t,MPFR_RNDD);
  if (!MPFR_IS_INF(ash) || MPFR_IS_NEG (ash)  || tester!=0)
    {
      printf("asinh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******atanh********/

  tester = mpfr_atanh (ath, t, MPFR_RNDD);
  if (!MPFR_IS_NAN(ath) || tester != 0)
    {
      printf("atanh(INF) \n");
      fail = 1;
      goto clean_up;
    }

  MPFR_CHANGE_SIGN(t);

  /******cosh********/

  tester=mpfr_cosh(ch,t,MPFR_RNDD);
  if (!MPFR_IS_INF(ch) || MPFR_IS_NEG (ch)  || tester!=0)
    {
      printf("cosh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******sinh********/

  tester=mpfr_sinh(sh,t,MPFR_RNDD);
  if (!MPFR_IS_INF(sh)  || MPFR_IS_POS (sh) || tester!=0)
    {
      printf("sinh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******tanh********/

  tester=mpfr_tanh(th,t,MPFR_RNDD);
  if (!mpfr_cmp_ui(th,-1) || tester!=0)
    {
      printf("tanh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******acosh********/

  tester=mpfr_acosh(ach,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ach) || tester!=0)
    {
      printf("acosh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******asinh********/

  tester=mpfr_asinh(ash,t,MPFR_RNDD);
  if (!MPFR_IS_INF(ash) || MPFR_IS_POS (ash)  || tester!=0)
    {
      printf("asinh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

  /******atanh********/

  tester = mpfr_atanh (ath, t, MPFR_RNDD);
  if (!MPFR_IS_NAN(ath) || tester != 0)
    {
      printf("atanh(-INF) \n");
      fail = 1;
      goto clean_up;
    }

 clean_up:
  mpfr_clear(t);
  mpfr_clear(ch);
  mpfr_clear(sh);
  mpfr_clear(th);
  mpfr_clear(ach);
  mpfr_clear(ash);
  mpfr_clear(ath);

  return fail;
}
示例#11
0
文件: thyperbolic.c 项目: Canar/mpfr
static int
check_zero (void)
{
  mpfr_t t, ch,sh,th,ach,ash,ath;
  int tester;
  int fail = 0;

  mpfr_init2(t,200);
  mpfr_init2(ch,200);
  mpfr_init2(sh,200);
  mpfr_init2(th,200);
  mpfr_init2(ach,200);
  mpfr_init2(ash,200);
  mpfr_init2(ath,200);

  mpfr_set_ui(t,0,MPFR_RNDD);

  /******cosh********/

  tester = mpfr_cosh (ch, t, MPFR_RNDD);
  if (mpfr_cmp_ui(ch, 1) || tester)
    {
      printf("cosh(0) \n");
      fail = 1;
      goto clean_up;
    }

  /******sinh********/

  tester = mpfr_sinh (sh, t, MPFR_RNDD);
  if (!MPFR_IS_ZERO(sh) || tester)
    {
      printf("sinh(0) \n");
      fail = 1;
      goto clean_up;
    }

  /******tanh********/

  tester = mpfr_tanh (th, t, MPFR_RNDD);
  if (!MPFR_IS_ZERO(th) || tester)
    {
      printf("tanh(0) \n");
      fail = 1;
      goto clean_up;
    }

  /******acosh********/

  tester=mpfr_acosh(ach,t,MPFR_RNDD);
  if (!MPFR_IS_NAN(ach) || tester)
    {
      printf("acosh(0) \n");
      fail = 1;
      goto clean_up;
    }

  /******asinh********/

  tester=mpfr_asinh(ash,t,MPFR_RNDD);
  if (!MPFR_IS_ZERO(ash) || tester)
    {
      printf("asinh(0) \n");
      fail = 1;
      goto clean_up;
    }

  /******atanh********/

  tester=mpfr_atanh(ath,t,MPFR_RNDD);
  if (!MPFR_IS_ZERO(ath) || tester)
    {
      printf("atanh(0) \n");
      fail = 1;
      goto clean_up;
    }

 clean_up:
  mpfr_clear(t);
  mpfr_clear(ch);
  mpfr_clear(sh);
  mpfr_clear(th);
  mpfr_clear(ach);
  mpfr_clear(ash);
  mpfr_clear(ath);

  return fail;
}
示例#12
0
文件: sinh.c 项目: Distrotech/mpfr
int
mpfr_sinh (mpfr_ptr y, mpfr_srcptr xt, mpfr_rnd_t rnd_mode)
{
  mpfr_t x;
  int inexact;

  MPFR_LOG_FUNC
    (("x[%Pu]=%.*Rg rnd=%d", mpfr_get_prec (xt), mpfr_log_prec, xt, rnd_mode),
     ("y[%Pu]=%.*Rg inexact=%d",
      mpfr_get_prec (y), mpfr_log_prec, y, inexact));

  if (MPFR_UNLIKELY (MPFR_IS_SINGULAR (xt)))
    {
      if (MPFR_IS_NAN (xt))
        {
          MPFR_SET_NAN (y);
          MPFR_RET_NAN;
        }
      else if (MPFR_IS_INF (xt))
        {
          MPFR_SET_INF (y);
          MPFR_SET_SAME_SIGN (y, xt);
          MPFR_RET (0);
        }
      else /* xt is zero */
        {
          MPFR_ASSERTD (MPFR_IS_ZERO (xt));
          MPFR_SET_ZERO (y);   /* sinh(0) = 0 */
          MPFR_SET_SAME_SIGN (y, xt);
          MPFR_RET (0);
        }
    }

  /* sinh(x) = x + x^3/6 + ... so the error is < 2^(3*EXP(x)-2) */
  MPFR_FAST_COMPUTE_IF_SMALL_INPUT (y, xt, -2 * MPFR_GET_EXP(xt), 2, 1,
                                    rnd_mode, {});

  MPFR_TMP_INIT_ABS (x, xt);

  {
    mpfr_t t, ti;
    mpfr_exp_t d;
    mpfr_prec_t Nt;    /* Precision of the intermediary variable */
    long int err;    /* Precision of error */
    MPFR_ZIV_DECL (loop);
    MPFR_SAVE_EXPO_DECL (expo);
    MPFR_GROUP_DECL (group);

    MPFR_SAVE_EXPO_MARK (expo);

    /* compute the precision of intermediary variable */
    Nt = MAX (MPFR_PREC (x), MPFR_PREC (y));
    /* the optimal number of bits : see algorithms.ps */
    Nt = Nt + MPFR_INT_CEIL_LOG2 (Nt) + 4;
    /* If x is near 0, exp(x) - 1/exp(x) = 2*x+x^3/3+O(x^5) */
    if (MPFR_GET_EXP (x) < 0)
      Nt -= 2*MPFR_GET_EXP (x);

    /* initialise of intermediary variables */
    MPFR_GROUP_INIT_2 (group, Nt, t, ti);

    /* First computation of sinh */
    MPFR_ZIV_INIT (loop, Nt);
    for (;;)
      {
        MPFR_BLOCK_DECL (flags);

        /* compute sinh */
        MPFR_BLOCK (flags, mpfr_exp (t, x, MPFR_RNDD));
        if (MPFR_OVERFLOW (flags))
          /* exp(x) does overflow */
          {
            /* sinh(x) = 2 * sinh(x/2) * cosh(x/2) */
            mpfr_div_2ui (ti, x, 1, MPFR_RNDD); /* exact */

            /* t <- cosh(x/2): error(t) <= 1 ulp(t) */
            MPFR_BLOCK (flags, mpfr_cosh (t, ti, MPFR_RNDD));
            if (MPFR_OVERFLOW (flags))
              /* when x>1 we have |sinh(x)| >= cosh(x/2), so sinh(x)
                 overflows too */
              {
                inexact = mpfr_overflow (y, rnd_mode, MPFR_SIGN (xt));
                MPFR_SAVE_EXPO_UPDATE_FLAGS (expo, MPFR_FLAGS_OVERFLOW);
                break;
              }

            /* ti <- sinh(x/2): , error(ti) <= 1 ulp(ti)
               cannot overflow because 0 < sinh(x) < cosh(x) when x > 0 */
            mpfr_sinh (ti, ti, MPFR_RNDD);

            /* multiplication below, error(t) <= 5 ulp(t) */
            MPFR_BLOCK (flags, mpfr_mul (t, t, ti, MPFR_RNDD));
            if (MPFR_OVERFLOW (flags))
              {
                inexact = mpfr_overflow (y, rnd_mode, MPFR_SIGN (xt));
                MPFR_SAVE_EXPO_UPDATE_FLAGS (expo, MPFR_FLAGS_OVERFLOW);
                break;
              }

            /* doubling below, exact */
            MPFR_BLOCK (flags, mpfr_mul_2ui (t, t, 1, MPFR_RNDN));
            if (MPFR_OVERFLOW (flags))
              {
                inexact = mpfr_overflow (y, rnd_mode, MPFR_SIGN (xt));
                MPFR_SAVE_EXPO_UPDATE_FLAGS (expo, MPFR_FLAGS_OVERFLOW);
                break;
              }

            /* we have lost at most 3 bits of precision */
            err = Nt - 3;
            if (MPFR_LIKELY (MPFR_CAN_ROUND (t, err, MPFR_PREC (y),
                                             rnd_mode)))
              {
                inexact = mpfr_set4 (y, t, rnd_mode, MPFR_SIGN (xt));
                break;
              }
            err = Nt; /* double the precision */
          }
        else
          {
            d = MPFR_GET_EXP (t);
            mpfr_ui_div (ti, 1, t, MPFR_RNDU); /* 1/exp(x) */
            mpfr_sub (t, t, ti, MPFR_RNDN);    /* exp(x) - 1/exp(x) */
            mpfr_div_2ui (t, t, 1, MPFR_RNDN);  /* 1/2(exp(x) - 1/exp(x)) */

            /* it may be that t is zero (in fact, it can only occur when te=1,
               and thus ti=1 too) */
            if (MPFR_IS_ZERO (t))
              err = Nt; /* double the precision */
            else
              {
                /* calculation of the error */
                d = d - MPFR_GET_EXP (t) + 2;
                /* error estimate: err = Nt-(__gmpfr_ceil_log2(1+pow(2,d)));*/
                err = Nt - (MAX (d, 0) + 1);
                if (MPFR_LIKELY (MPFR_CAN_ROUND (t, err, MPFR_PREC (y),
                                                 rnd_mode)))
                  {
                    inexact = mpfr_set4 (y, t, rnd_mode, MPFR_SIGN (xt));
                    break;
                  }
              }
          }

        /* actualisation of the precision */
        Nt += err;
        MPFR_ZIV_NEXT (loop, Nt);
        MPFR_GROUP_REPREC_2 (group, Nt, t, ti);
      }
    MPFR_ZIV_FREE (loop);
    MPFR_GROUP_CLEAR (group);
    MPFR_SAVE_EXPO_FREE (expo);
  }

  return mpfr_check_range (y, inexact, rnd_mode);
}
示例#13
0
MpfrFloat MpfrFloat::cosh(const MpfrFloat& value)
{
    MpfrFloat retval(MpfrFloat::kNoInitialization);
    mpfr_cosh(retval.mData->mFloat, value.mData->mFloat, GMP_RNDN);
    return retval;
}
示例#14
0
static void
special (void)
{
  mpfr_t  x, y;
  int i;

  mpfr_init (x);
  mpfr_init (y);

  mpfr_set_nan (x);
  mpfr_cosh (y, x, GMP_RNDN);
  if (!mpfr_nan_p (y))
    {
      printf ("Error: cosh(NaN) != NaN\n");
      exit (1);
    }

  mpfr_set_inf (x, 1);
  mpfr_cosh (y, x, GMP_RNDN);
  if (!mpfr_inf_p (y) || mpfr_sgn (y) < 0)
    {
      printf ("Error: cosh(+Inf) != +Inf\n");
      exit (1);
    }

  mpfr_set_inf (x, -1);
  mpfr_cosh (y, x, GMP_RNDN);
  if (!mpfr_inf_p (y) || mpfr_sgn (y) < 0)
    {
      printf ("Error: cosh(-Inf) != +Inf\n");
      exit (1);
    }

  /* cosh(+/-0) = 1 */
  mpfr_set_ui (x, 0, GMP_RNDN);
  mpfr_cosh (y, x, GMP_RNDN);
  if (mpfr_cmp_ui (y, 1))
    {
      printf ("Error: cosh(+0) != 1\n");
      exit (1);
    }
  mpfr_neg (x, x, GMP_RNDN);
  mpfr_cosh (y, x, GMP_RNDN);
  if (mpfr_cmp_ui (y, 1))
    {
      printf ("Error: cosh(-0) != 1\n");
      exit (1);
    }

  mpfr_set_prec (x, 32);
  mpfr_set_prec (y, 32);

  mpfr_set_str_binary (x, "0.1101110111111111001011101000101");
  mpfr_set_str_binary (y, "1.0110011001110000101100011001001");
  mpfr_cosh (x, x, GMP_RNDN);
  if (mpfr_cmp (x, y))
    {
      printf ("Error: mpfr_cosh for prec=32 (1)\n");
      exit (1);
    }

  mpfr_set_str_binary (x, "-0.1110111000011101010111100000101E-1");
  mpfr_set_str_binary (y, "1.0001110000101111111111100110101");
  mpfr_cosh (x, x, GMP_RNDN);
  if (mpfr_cmp (x, y))
    {
      printf ("Error: mpfr_cosh for prec=32 (2)\n");
      exit (1);
    }

  mpfr_set_prec (x, 2);
  mpfr_clear_flags ();
  mpfr_set_str_binary (x, "1E1000000000");
  i = mpfr_cosh (x, x, GMP_RNDN);
  MPFR_ASSERTN (MPFR_IS_INF (x) && MPFR_SIGN (x) > 0);
  MPFR_ASSERTN (mpfr_overflow_p ());
  MPFR_ASSERTN (i == 1);

  mpfr_clear_flags ();
  mpfr_set_str_binary (x, "-1E1000000000");
  i = mpfr_cosh (x, x, GMP_RNDN);
  MPFR_ASSERTN (MPFR_IS_INF (x) && MPFR_SIGN (x) > 0);
  MPFR_ASSERTN (mpfr_overflow_p () && !mpfr_underflow_p ());
  MPFR_ASSERTN (i == 1);

  mpfr_clear_flags ();
  mpfr_set_str_binary (x, "-1E1000000000");
  i = mpfr_cosh (x, x, GMP_RNDD);
  MPFR_ASSERTN (!MPFR_IS_INF (x) && MPFR_SIGN (x) > 0);
  MPFR_ASSERTN (mpfr_overflow_p () && !mpfr_underflow_p ());
  MPFR_ASSERTN (i == -1);

  mpfr_clear_flags ();
  mpfr_set_str_binary (x, "-1E1000000000");
  i = mpfr_cosh (x, x, GMP_RNDU);
  MPFR_ASSERTN (MPFR_IS_INF (x) && MPFR_SIGN (x) > 0);
  MPFR_ASSERTN (mpfr_overflow_p () && !mpfr_underflow_p ());
  MPFR_ASSERTN (i == 1);

  mpfr_clear (x);
  mpfr_clear (y);
}
示例#15
0
 void bvisit(const Cosh &x) {
     apply(result_, *(x.get_arg()));
     mpfr_cosh(result_, result_, rnd_);
 }
示例#16
0
文件: cos.c 项目: 119/aircam-openwrt
int
mpc_cos (mpc_ptr rop, mpc_srcptr op, mpc_rnd_t rnd)
{
  mpfr_t x, y, z;
  mp_prec_t prec;
  int ok = 0;
  int inex_re, inex_im;

  /* special values */
  if (!mpfr_number_p (MPC_RE (op)) || !mpfr_number_p (MPC_IM (op)))
    {
      if (mpfr_nan_p (MPC_RE (op)))
        {
          /* cos(NaN + i * NaN) = NaN + i * NaN */
          /* cos(NaN - i * Inf) = +Inf + i * NaN */
          /* cos(NaN + i * Inf) = +Inf + i * NaN */
          /* cos(NaN - i * 0) = NaN - i * 0 */
          /* cos(NaN + i * 0) = NaN + i * 0 */
          /* cos(NaN + i * y) = NaN + i * NaN, when y != 0 */
          if (mpfr_inf_p (MPC_IM (op)))
            mpfr_set_inf (MPC_RE (rop), +1);
          else
            mpfr_set_nan (MPC_RE (rop));

          if (mpfr_zero_p (MPC_IM (op)))
            mpfr_set (MPC_IM (rop), MPC_IM (op), MPC_RND_IM (rnd));
          else
            mpfr_set_nan (MPC_IM (rop));
        }
      else if (mpfr_nan_p (MPC_IM (op)))
        {
          /* cos(-Inf + i * NaN) = NaN + i * NaN */
          /* cos(+Inf + i * NaN) = NaN + i * NaN */
          /* cos(-0 + i * NaN) = NaN - i * 0 */
          /* cos(+0 + i * NaN) = NaN + i * 0 */
          /* cos(x + i * NaN) = NaN + i * NaN, when x != 0 */
          if (mpfr_zero_p (MPC_RE (op)))
            mpfr_set (MPC_IM (rop), MPC_RE (op), MPC_RND_IM (rnd));
          else
            mpfr_set_nan (MPC_IM (rop));

          mpfr_set_nan (MPC_RE (rop));
        }
      else if (mpfr_inf_p (MPC_RE (op)))
        {
          /* cos(-Inf -i*Inf) = cos(+Inf +i*Inf) = -Inf +i*NaN */
          /* cos(-Inf +i*Inf) = cos(+Inf -i*Inf) = +Inf +i*NaN */
          /* cos(-Inf -i*0) = cos(+Inf +i*0) = NaN -i*0 */
          /* cos(-Inf +i*0) = cos(+Inf -i*0) = NaN +i*0 */
          /* cos(-Inf +i*y) = cos(+Inf +i*y) = NaN +i*NaN, when y != 0 */

          /* SAME_SIGN is useful only if op == (+/-)Inf + i * (+/-)0, but, as
             MPC_RE(OP) might be erased (when ROP == OP), we compute it now */
          const int same_sign =
            mpfr_signbit (MPC_RE (op)) == mpfr_signbit (MPC_IM (op));

          if (mpfr_inf_p (MPC_IM (op)))
            mpfr_set_inf (MPC_RE (rop), (same_sign ? -1 : +1));
          else
            mpfr_set_nan (MPC_RE (rop));

          if (mpfr_zero_p (MPC_IM (op)))
            mpfr_setsign (MPC_IM (rop), MPC_IM (op), same_sign,
                          MPC_RND_IM(rnd));
          else
            mpfr_set_nan (MPC_IM (rop));
        }
      else if (mpfr_zero_p (MPC_RE (op)))
        {
          /* cos(-0 -i*Inf) = cos(+0 +i*Inf) = +Inf -i*0 */
          /* cos(-0 +i*Inf) = cos(+0 -i*Inf) = +Inf +i*0 */
          const int same_sign =
            mpfr_signbit (MPC_RE (op)) == mpfr_signbit (MPC_IM (op));

          mpfr_setsign (MPC_IM (rop), MPC_RE (op), same_sign,
                        MPC_RND_IM (rnd));
          mpfr_set_inf (MPC_RE (rop), +1);
        }
      else
        {
          /* cos(x -i*Inf) = +Inf*cos(x) +i*Inf*sin(x), when x != 0 */
          /* cos(x +i*Inf) = +Inf*cos(x) -i*Inf*sin(x), when x != 0 */
          mpfr_t c;
          mpfr_t s;

          mpfr_init (c);
          mpfr_init (s);

          mpfr_sin_cos (s, c, MPC_RE (op), GMP_RNDN);
          mpfr_set_inf (MPC_RE (rop), mpfr_sgn (c));
          mpfr_set_inf (MPC_IM (rop),
                        (mpfr_sgn (MPC_IM (op)) == mpfr_sgn (s) ? -1 : +1));

          mpfr_clear (s);
          mpfr_clear (c);
        }

      return MPC_INEX (0, 0); /* always exact */
    }

  if (mpfr_zero_p (MPC_RE (op)))
    {
      /* cos(-0 - i * y) = cos(+0 + i * y) = cosh(y) - i * 0
         cos(-0 + i * y) = cos(+0 - i * y) = cosh(y) + i * 0,
         when y >= 0 */

      /* When ROP == OP, the sign of 0 will be erased, so use it now */
      const int imag_sign =
        mpfr_signbit (MPC_RE (op)) ==  mpfr_signbit (MPC_IM (op));

      if (mpfr_zero_p (MPC_IM (op)))
        inex_re = mpfr_set_ui (MPC_RE (rop), 1, MPC_RND_RE (rnd));
      else
        inex_re = mpfr_cosh (MPC_RE (rop), MPC_IM (op), MPC_RND_RE (rnd));

      mpfr_set_ui (MPC_IM (rop), 0, MPC_RND_IM (rnd));
      mpfr_setsign (MPC_IM (rop), MPC_IM (rop), imag_sign, MPC_RND_IM (rnd));

      return MPC_INEX (inex_re, 0);
    }

  if (mpfr_zero_p (MPC_IM (op)))
    {
      /* cos(x +i*0) = cos(x) -i*0*sign(sin(x)) */
      /* cos(x -i*0) = cos(x) +i*0*sign(sin(x)) */
      mpfr_t sign;
      mpfr_init2 (sign, 2);
      mpfr_sin (sign, MPC_RE (op), GMP_RNDN);
      if (!mpfr_signbit (MPC_IM (op)))
         MPFR_CHANGE_SIGN (sign);

      inex_re = mpfr_cos (MPC_RE (rop), MPC_RE (op), MPC_RND_RE (rnd));

      mpfr_set_ui (MPC_IM (rop), 0ul, GMP_RNDN);
      if (mpfr_signbit (sign))
         MPFR_CHANGE_SIGN (MPC_IM (rop));

      mpfr_clear (sign);

      return MPC_INEX (inex_re, 0);
    }

  /* ordinary (non-zero) numbers */

  /* let op = a + i*b, then cos(op) = cos(a)*cosh(b) - i*sin(a)*sinh(b).

     We use the following algorithm (same for the imaginary part),
     with rounding to nearest for all operations, and working precision w:

     (1) x = o(cos(a))
     (2) y = o(cosh(b))
     (3) r = o(x*y)
     then the error on r is at most 4 ulps, since we can write
     r = cos(a)*cosh(b)*(1+t)^3 with |t| <= 2^(-w),
     thus for w >= 2, r = cos(a)*cosh(b)*(1+4*t) with |t| <= 2^(-w),
     thus the relative error is bounded by 4*2^(-w) <= 4*ulp(r).
  */

  prec = MPC_MAX_PREC(rop);

  mpfr_init2 (x, 2);
  mpfr_init2 (y, 2);
  mpfr_init2 (z, 2);

  do
    {
      prec += mpc_ceil_log2 (prec) + 5;

      mpfr_set_prec (x, prec);
      mpfr_set_prec (y, prec);
      mpfr_set_prec (z, prec);

      mpfr_sin_cos (y, x, MPC_RE(op), GMP_RNDN);
      mpfr_cosh (z, MPC_IM(op), GMP_RNDN);
      mpfr_mul (x, x, z, GMP_RNDN);
      ok = mpfr_can_round (x, prec - 2, GMP_RNDN, GMP_RNDZ,
                      MPFR_PREC(MPC_RE(rop)) + (MPC_RND_RE(rnd) == GMP_RNDN));
      if (ok) /* compute imaginary part */
        {
          mpfr_sinh (z, MPC_IM(op), GMP_RNDN);
          mpfr_mul (y, y, z, GMP_RNDN);
          mpfr_neg (y, y, GMP_RNDN);
          ok = mpfr_can_round (y, prec - 2, GMP_RNDN, GMP_RNDZ,
                      MPFR_PREC(MPC_IM(rop)) + (MPC_RND_IM(rnd) == GMP_RNDN));
        }
    }
  while (ok == 0);

  inex_re = mpfr_set (MPC_RE(rop), x, MPC_RND_RE(rnd));
  inex_im = mpfr_set (MPC_IM(rop), y, MPC_RND_IM(rnd));

  mpfr_clear (x);
  mpfr_clear (y);
  mpfr_clear (z);

  return MPC_INEX (inex_re, inex_im);
}