abacus: bignum: add is_canonicalized predicate
Useful when debugging.
This commit is contained in:
parent
12c8b6b114
commit
2cff603a48
|
@ -2,6 +2,7 @@
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
|
#include <cassert>
|
||||||
#include <cmath>
|
#include <cmath>
|
||||||
|
|
||||||
namespace abacus::bignum {
|
namespace abacus::bignum {
|
||||||
|
@ -22,6 +23,8 @@ BigNum::BigNum(std::int64_t number) {
|
||||||
digits_.push_back(abs % 10);
|
digits_.push_back(abs % 10);
|
||||||
abs /= 10;
|
abs /= 10;
|
||||||
} while (abs);
|
} while (abs);
|
||||||
|
|
||||||
|
assert(is_canonicalized());
|
||||||
}
|
}
|
||||||
|
|
||||||
void BigNum::canonicalize() {
|
void BigNum::canonicalize() {
|
||||||
|
@ -32,6 +35,28 @@ void BigNum::canonicalize() {
|
||||||
if (digits_.size() == 0) {
|
if (digits_.size() == 0) {
|
||||||
sign_ = 0;
|
sign_ = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
assert(is_canonicalized());
|
||||||
|
}
|
||||||
|
|
||||||
|
bool BigNum::is_canonicalized() const {
|
||||||
|
if (digits_.size() == 0) {
|
||||||
|
return sign_ == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto const leading_zeros = std::find_if(digits_.rbegin(), digits_.rend(),
|
||||||
|
[](auto v) { return v != 0; });
|
||||||
|
if (leading_zeros != digits_.rbegin()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto const overflow = std::find_if(digits_.begin(), digits_.end(),
|
||||||
|
[](auto v) { return v >= 10; });
|
||||||
|
if (overflow != digits_.end()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace abacus::bignum
|
} // namespace abacus::bignum
|
||||||
|
|
|
@ -12,6 +12,7 @@ public:
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void canonicalize();
|
void canonicalize();
|
||||||
|
bool is_canonicalized() const;
|
||||||
|
|
||||||
std::vector<std::uint8_t> digits_{};
|
std::vector<std::uint8_t> digits_{};
|
||||||
int sign_ = 0;
|
int sign_ = 0;
|
||||||
|
|
Loading…
Reference in a new issue