Example #1
0
// -------------------------------------------- compare
// returns 1 if a > b, 0 if a == b and -1 otherwise.
int compare (const Rational& a, const Rational &b)
{
  if (isZero(a.num) && isZero(b.num))
      return 0 ;
  if (isZero(a.num))
      return -sign(b.num);
  if (isZero(b.num))
      return sign(a.num);
  if (sign(a.num) != sign(b.num))
      return (sign(a.num) == -1 ? -1 : 1 )  ;
  if (sign(a.num) > 0)
      return absCompare(a,b) ;
  else return -absCompare(a,b) ;
}
Example #2
0
BigInt& BigInt::operator -= (const BigInt &bi)
{
    NumVec vec;

    if( m_sign ^ bi.m_sign )
    {
        vec = BigInt::vecAdd(m_vec, bi.m_vec);
    }
    else
    {
        if( absCompare(bi) >= 0 )
        {
            vec = BigInt::vecSub(m_vec, bi.m_vec);
        }
        else
        {
            vec = BigInt::vecSub(bi.m_vec, m_vec);
            m_sign = !bi.m_sign;
        }

        if( vec.size()==1 && vec[0] == 0)
            m_sign = false;
    }

    m_vec = std::move(vec);

    return *this;
}
Example #3
0
	int32_t absCompare(const Integer &a, const int64_t b)
	{
#if GMP_LIMB_BITS != 64
		return absCompare( a, Integer(b));
#else
		return mpz_cmpabs_ui( (mpz_srcptr)&(a.gmp_rep), (uint64_t) std::abs(b));
#endif
	}
Example #4
0
// -------------------------------------------- absCompare
int absCompare (const Rational& a, const Rational& b)
{
  int cnum = absCompare(a.num, b.num) ;
  int cden = absCompare(a.den, b.den) ;

  if ( (cnum == -1) && (cden == 1) )
    return -1 ;
  if ( (cnum == 1) && (cden == -1) )
    return 1 ;
  if (cnum == 0)
    return -cden ;
  if (cden == 0)
    return cnum ;

  Integer p1 = a.num * b.den;
  Integer p2 = a.den * b.num;
  return absCompare(p1,p2);
}
Example #5
0
BigInt& BigInt::operator /= (const BigInt &bi)
{
    if( bi == 0 )
        throw std::logic_error("can't div 0");

    bool sign = m_sign;
    m_sign = false;

    BigInt res(0);

    BigInt divsor(bi), count(1);
    while( absCompare(divsor) >= 0 )
    {
        divsor.selfLeftShift(10);//fast
        count.selfLeftShift(10);
    }

    while(absCompare(bi) >= 0)
    {
        while(absCompare(divsor) < 0)
        {
            divsor.selfRightShift(1);//slow
            count.selfRightShift(1);
        }

        res += count;
        (*this) -= divsor;
    }

    m_vec = std::move(res.m_vec);
    if( m_vec.size() == 1 && m_vec[0] == 0 )
        m_sign = false;
    else
        m_sign = sign ^ bi.m_sign;

    return *this;
}
Example #6
0
bool BigInt::operator > (const BigInt &bi)const
{
    if( m_sign != bi.m_sign )
        return !m_sign;

    int ret = absCompare(bi);
    if( ret == 0 )
        return false;

    //当同为正数时(m_sign为false),对于正数来说,直接判断ret是否大于0即可。
    //此时异或的结果也是根据ret>0而确定的.
    //当同为负数时(m_sign为true),对于负数来说,结果要与ret>0取反,
    //而异或在m_sign为true时会自动与ret>0取反.
    return m_sign ^ (ret > 0);
}
Example #7
0
bool BigInt::operator < (const BigInt &bi)const
{
    if( m_sign != bi.m_sign )
        return m_sign;

    //same sign
    int ret = absCompare(bi);
    if( ret == 0 )
        return false;

    /*
    if( m_sign )//negative
        return ret > 0;
    else //positive
        return ret < 0;
    */
    return m_sign ^ (ret < 0);
}