It was a draft PR, not ready for merging, and its premature inclusion
caused repeated issues, see 368f47381b & friends.
Close#1841.
This reverts commits 3743a3e1e7,
ce218e01b6, and
b7b0c76b8e.
* factor::tests::recombines_factors: Minor refactor (skip useless bool)
* factor::tests: Check factorizations of powers of factored numbers
* factor::Factors: Add debug assertions to (Factor ^ Exponent)
* factor::tests: Drop obsoleted tests
`factor_correctly_recombines_prior_test_failures` was replaced with
`factor_2044854919485649` as this was the only test not subsumed.
* factor::tests::2044854919485649: Check the expected factorisation
* factor: Confine knowledge of num_traits to numeric::traits
This should make it easier to deal with API changes of num_traits,
or eventually switching to an abstraction provided in the stdlib.
- refactor internal version specifications to be ">=M.m.p" (where M.m.p is *already published*)
## [why]
Loosening internal version dependencies decreases the coupling between packages such
that packages can be published in a looser order. It allows the packages to be version
updated and published in tandem (ie, by using `cargo workspace ...`). Once published,
the internal versions can then be updated (again, to an *already published* package
version), as needed.
This avoids allocating on the heap when factoring most numbers,
without using much space on the stack.
This is ~3.5% faster than the previous commit, and ~8.3% faster than “master”.
The invariant is checked by a debug_assert!, and follows from the previous
commit, as `dec` and `factors` only ever contains coprime numbers:
- true at the start: factor = ∅ and dec = { n¹ } ;
- on every loop iteration, we pull out an element `f` from `dec` and either:
- discover it is prime, and add it to `factors` ;
- split it into a number of coprime factors, that get reinserted into `dec`;
the invariant is maintained, as all divisors of `f` are coprime with all
numbers in `dec` and `factors` (as `f` itself is coprime with them.
As we only add elements to `Decomposition` objects that are coprime with the
existing ones, they are distinct.
* factor: Introduce a type alias for exponents
This way, we can easily replace u8 with a larger type when moving to support
larger integers.
* factor::Factors: Split off a Decomposition type
The new type can be used to represent in-progress factorisations,
which contain non-prime factors.
* factor::Decomposition: Use a flat vector representation
~18% faster than BTreeMap, and ~5% faster than “master”.
* factor::Factors: Use a RefCell rather than copy data when printing
~2.9% faster than the previous commit, ~11% faster than “master” overall.
* CI: Only run rustfmt in one environment
- This displays clippy warnings even when rustfmt fails.
- This avoids displaying 3 copies of the same rustfmt warning as Github
annotations.
- Avoids duplicated work.
* CI: Suppress warnings when building for the oldest toolchain version
We had cases of warnings emitted due to `rustc` bugs that were fixed
in non-obsolete versions.
* factor: Remove a workaround for warnings on obsolete rustc
* factor::numeric::gcd: Switch variable names to be more consistent
* factor::numeric::gcd: Improve comments
* factor::numeric::gcd: Extend loop invariant to v
* factor::Factors: Derive implementations of Eq and PartialEq
* factors::Factors: Implement quickcheck::Arbitrary
This generates uniformly-distributed integers with known factorisations,
and will enable further testing.
* factor: Test against random numbers with known factorisations
* factor::Factors::arbitrary: Simplify method signature
* factor::numeric::gcd: Rename test against the Euclidean algorithm
* factor::numeric::gcd: Add various property-based tests
* factor::numeric::modular_inverse: Rename test
* factor::numeric::modular_inverse: Add test on random values
* factor::numeric: Start refactoring into multiple submodules
No change to the module's interface, but it should make it much easier to
keep the tests right next to the code they are related to.
Moreover, build.rs' dependency is now limited to numeric::{modular_inverse,
traits}, meaning that the rest of it can use build-time generated tables etc.
* factor::numeric: Move gcd (and its test) to a submodule
* factor::numeric: Move Montgomery arithmetic to its own module
Finally hollowed-out numeric.rs
* factor: Move numeric.rs to numeric/mod.rs
* factor::numeric: Fix an erroneous lint on obsolete Rust versions
Ignoring a value of that type is a bug: they are only produced by
`miller_rabbin::test`, which is a pure, but expensive, function.
As such, an ignored value is always either a mistake, or an easy
optimisation opportunity (just remove the useless call to `test`).