Compare commits

...

2 commits

Author SHA1 Message Date
Bruno BELANYI c9460c09d5 abacus: bignum: simplify is_canonicalized
All checks were successful
continuous-integration/drone/push Build is passing
2022-02-17 10:13:29 +01:00
Bruno BELANYI a382b299b0 abacus: bignum: fix comparison of negative numbers 2022-02-17 10:03:21 +01:00
2 changed files with 39 additions and 7 deletions

View file

@ -363,7 +363,11 @@ bool BigNum::less_than(BigNum const& rhs) const {
return sign_ < rhs.sign_;
}
return do_less_than(digits_, rhs.digits_);
if (is_positive()) {
return do_less_than(digits_, rhs.digits_);
} else {
return do_less_than(rhs.digits_, digits_);
}
}
void BigNum::canonicalize() {
@ -381,15 +385,15 @@ bool BigNum::is_canonicalized() const {
return sign_ == 0;
}
auto const leading_zeros = std::find_if(digits_.rbegin(), digits_.rend(),
[](auto v) { return v != 0; });
if (leading_zeros != digits_.rbegin()) {
// `back` is valid since there is at least one element
auto const has_leading_zero = digits_.back() == 0;
if (has_leading_zero) {
return false;
}
auto const overflow = std::find_if(digits_.begin(), digits_.end(),
[](auto v) { return v >= BASE; });
if (overflow != digits_.end()) {
auto const has_overflow = std::any_of(digits_.begin(), digits_.end(),
[](auto v) { return v >= BASE; });
if (has_overflow) {
return false;
}

View file

@ -68,6 +68,34 @@ TEST(BigNum, comparisons_digits) {
EXPECT_GT(ten, nine);
}
TEST(BigNum, comparisons_negative) {
auto const zero = BigNum(0);
auto const minus_one = BigNum(-1);
auto const minus_two = BigNum(-2);
EXPECT_LT(minus_one, zero);
EXPECT_LE(minus_one, zero);
EXPECT_LT(minus_two, minus_one);
EXPECT_LE(minus_two, minus_one);
EXPECT_LE(minus_one, minus_one);
EXPECT_GE(minus_two, minus_two);
EXPECT_GT(zero, minus_one);
EXPECT_GE(zero, minus_one);
EXPECT_GT(minus_one, minus_two);
EXPECT_GE(minus_one, minus_two);
EXPECT_GE(minus_one, minus_one);
EXPECT_GE(minus_two, minus_two);
}
TEST(BigNum, comparisons_digits_negative) {
auto const minus_nine = BigNum(-9);
auto const minus_ten = BigNum(-10);
EXPECT_LT(minus_ten, minus_nine);
EXPECT_GT(minus_nine, minus_ten);
}
TEST(BigNum, unary) {
auto const zero = BigNum(0);
auto const one = BigNum(1);