Exemple #1
0
char
_doshift(
  floatnum dest,
  cfloatnum x,
  cfloatnum shift,
  char right)
{
  int ishift;
  t_longint lx;

  if (float_isnan(shift))
    return _seterror(dest, NoOperand);
  if (!float_isinteger(shift))
    return _seterror(dest, OutOfDomain);
  if(!_cvtlogic(&lx, x))
    return 0;
  if (float_iszero(shift))
  {
    float_copy(dest, x, EXACT);
    return 1;
  }
  ishift = float_asinteger(shift);
  if (ishift == 0)
    ishift = (3*LOGICRANGE) * float_getsign(shift);
  if (!right)
    ishift = -ishift;
  if (ishift > 0)
    _shr(&lx, ishift);
  else
    _shl(&lx, -ishift);
  _logic2floatnum(dest, &lx);
  return 1;
}
Exemple #2
0
char
float_gamma(
  floatnum x,
  int digits)
{
  signed char sign;
  char result;

  if (!chckmathparam(x, digits))
    return 0;
  sign = float_getsign(x);
  if (float_isinteger(x))
  {
    if (sign <= 0)
      return _seterror(x, ZeroDivide);
    result = _gammaint(x, digits);
  }
  else if (float_getlength(x) - float_getexponent(x) == 2
           && float_getdigit(x, float_getlength(x) - 1) == 5)
    result = _gamma0_5(x, digits);
  else
    result = _gamma(x, digits);
  if (!result)
  {
    if (sign < 0)
      float_seterror(Underflow);
    else
      float_seterror(Overflow);
    float_setnan(x);
  }
  return result;
}
Exemple #3
0
char
_pochhammer(
  floatnum x,
  cfloatnum n,
  int digits)
{
  if (float_isinteger(n))
    return _pochhammer_i(x, n, digits);
  return _pochhammer_g(x, n, digits);
}
static Error
_outcompl(
  p_otokens tokens,
  floatnum x,
  p_number_desc n,
  int scale)
{
  (void)scale;

  if (!float_isinteger(x))
    return IOInvalidComplement;
  if (n->prefix.sign == IO_SIGN_MINUS)
    n->prefix.sign = IO_SIGN_COMPLEMENT;
  else
    n->prefix.sign = IO_SIGN_NONE;
  return _outfixphex(tokens, x, n, 0);
}
Exemple #5
0
char
float_raise(
  floatnum power,
  cfloatnum base,
  cfloatnum exponent,
  int digits)
{
  signed char sgn;

  if (float_isnan(exponent) || float_isnan(base))
    return _seterror(power, NoOperand);
  if (digits <= 0 || digits > MATHPRECISION)
    return _seterror(power, InvalidPrecision);
  if (float_iszero(base))
  {
    switch(float_getsign(exponent))
    {
    case 0:
      return _seterror(power, OutOfDomain);
    case -1:
      return _seterror(power, ZeroDivide);
    }
    return _setzero(power);
  }
  sgn = float_getsign(base);
  if (sgn < 0)
  {
    if (!float_isinteger(exponent))
      return _seterror(power, OutOfDomain);
    if ((float_getdigit(exponent, float_getexponent(exponent)) & 1) == 0)
      sgn = 1;
  }
  float_copy(power, base, digits+1);
  float_abs(power);
  if (!_raise(power, exponent, digits))
  {
    float_seterror(Overflow);
    if (float_getexponent(base) * float_getsign(exponent) < 0)
      float_seterror(Underflow);
    return _setnan(power);
  }
  float_setsign(power, sgn);
  return 1;
}
Exemple #6
0
static char
_pochhammer_i(
  floatnum x,
  cfloatnum n,
  int digits)
{
  /* do not use the expensive Gamma function when a few
     multiplications do the same */
  /* pre: n is an integer */
  int ni;
  signed char result;

  if (float_iszero(n))
    return float_copy(x, &c1, EXACT);
  if (float_isinteger(x))
  {
    result = -1;
    float_neg((floatnum)n);
    if (float_getsign(x) <= 0 && float_cmp(x, n) > 0)
      /* x and x+n have opposite signs, meaning 0 is
         among the factors */
      result = _setzero(x);
    else if (float_getsign(x) > 0 && float_cmp(x, n) <= 0)
      /* x and x+n have opposite signs, meaning at one point
      you have to divide by 0 */
      result = _seterror(x, ZeroDivide);
    float_neg((floatnum)n);
    if (result >= 0)
      return result;
  }
  if (float_getexponent(x) < EXPMAX/100)
  {
    ni = float_asinteger(n);
    if (ni != 0 && ni < 50 && ni > -50)
      return _pochhammer_si(x, ni, digits+2);
  }
  return _pochhammer_g(x, n, digits);
}