pub struct ComparableGaussianInteger(pub GaussianInteger);Expand description
ComparableGaussianInteger is a wrapper around a GaussianInteger, taking the
GaussianInteger by value.
The complex numbers have no total order compatible with their arithmetic, so GaussianInteger
does not implement Ord. Sometimes a canonical order is wanted anyway: for sorting a list of
Gaussian integers, or for using them as keys in a BTreeMap or
a BTreeSet. Wrapping a GaussianInteger in a
ComparableGaussianInteger provides one: values are compared lexicographically, first by real
part and then by imaginary part. This order is total, and equality under it agrees with
GaussianInteger equality; it just isn’t arithmetically meaningful.
The analogous wrapper for Floats is
ComparableFloat, although that wrapper also changes equality behavior, something that isn’t
necessary here.
ComparableGaussianInteger owns its value. This is useful in many cases, for example if you
want to use GaussianIntegers as keys in a map. In other situations, it is better to use
ComparableGaussianIntegerRef, which only has a reference to its value.
Tuple Fields§
§0: GaussianIntegerImplementations§
Source§impl ComparableGaussianInteger
impl ComparableGaussianInteger
Sourcepub const fn as_ref(&self) -> ComparableGaussianIntegerRef<'_>
pub const fn as_ref(&self) -> ComparableGaussianIntegerRef<'_>
Borrows a ComparableGaussianInteger as a ComparableGaussianIntegerRef.
§Worst-case complexity
Constant time and additional memory.
§Examples
use malachite_base::num::basic::traits::I;
use malachite_nz::gaussian_integer::{
ComparableGaussianInteger, ComparableGaussianIntegerRef, GaussianInteger,
};
let x = ComparableGaussianInteger(GaussianInteger::I);
assert_eq!(
x.as_ref(),
ComparableGaussianIntegerRef(&GaussianInteger::I)
);Methods from Deref<Target = GaussianInteger>§
Sourcepub fn checked_roots(&self, exp: u64) -> Vec<Self>
pub fn checked_roots(&self, exp: u64) -> Vec<Self>
Returns all the $n$th roots of a GaussianInteger: none if it is not a perfect $n$th
power, one if it is zero, and otherwise $\gcd(n, 4)$ of them, in the canonical order of
ComparableGaussianInteger,
lexicographic by real part and then imaginary part.
The principal root is the one whose argument lies in $(-\pi/g, \pi/g]$ for $g = \gcd(n, 4)$;
see CheckedRoot.
$$ f(z, n) = \{ w \in \Z[i] : w^n = z \}. $$
§Worst-case complexity
$T(n) = O(n^2)$
$M(n) = O(n)$
where $T$ is time, $M$ is additional memory, and $n$ is the maximum number of significant
bits of the real and imaginary parts of self.
§Panics
Panics if exp is zero.
§Examples
use malachite_base::num::basic::traits::Zero;
use malachite_nz::gaussian_integer::GaussianInteger;
use std::str::FromStr;
let roots = |s, exp| {
GaussianInteger::from_str(s)
.unwrap()
.checked_roots(exp)
.iter()
.map(ToString::to_string)
.collect::<Vec<_>>()
};
assert_eq!(roots("-4", 4), ["-1-i", "-1+i", "1-i", "1+i"]);
assert_eq!(roots("-4", 2), ["-2i", "2i"]);
assert_eq!(roots("-8", 3), ["-2"]);
assert_eq!(roots("3+4i", 3), Vec::<String>::new());
assert_eq!(
GaussianInteger::ZERO.checked_roots(7),
[GaussianInteger::ZERO]
);Sourcepub fn checked_sqrts(&self) -> Vec<Self>
pub fn checked_sqrts(&self) -> Vec<Self>
Returns all the square roots of a GaussianInteger: none if it is not a perfect square,
one if it is zero, and otherwise the principal root and its negative, in the canonical order
of ComparableGaussianInteger,
lexicographic by real part and then imaginary part.
The principal root is the one with positive real part or, if that is zero, with non-negative
imaginary part; see CheckedSqrt.
$$ f(z) = \{ w \in \Z[i] : w^2 = z \}. $$
§Worst-case complexity
$T(n) = O(n \log n \log\log n)$
$M(n) = O(n \log n)$
where $T$ is time, $M$ is additional memory, and $n$ is the maximum number of significant
bits of the real and imaginary parts of self.
§Examples
use malachite_base::num::basic::traits::Zero;
use malachite_nz::gaussian_integer::GaussianInteger;
use std::str::FromStr;
let roots = |s| {
GaussianInteger::from_str(s)
.unwrap()
.checked_sqrts()
.iter()
.map(ToString::to_string)
.collect::<Vec<_>>()
};
assert_eq!(roots("3+4i"), ["-2-i", "2+i"]);
assert_eq!(roots("-1"), ["-i", "i"]);
assert_eq!(roots("2+i"), Vec::<String>::new());
assert_eq!(
GaussianInteger::ZERO.checked_sqrts(),
[GaussianInteger::ZERO]
);Sourcepub fn remove_one_plus_i(&self) -> (Self, u64)
pub fn remove_one_plus_i(&self) -> (Self, u64)
Removes the largest power of $1 + i$ from a GaussianInteger, taking it by reference and
returning the reduced GaussianInteger together with the exponent of that power.
$1 + i$ is the Gaussian prime above 2, with $(1 + i)^2 = 2i$. If $(1 + i)^k$ is the largest
power of $1 + i$ that divides self, this returns $(\text{self} / (1 + i)^k, k)$. The
exponent is twice the largest power of 2 dividing both parts, plus one more when the parts
have the same 2-adic valuation, since then both are odd after the shift and their sum is
even. Zero is left alone, with an exponent of 0, since every power of $1 + i$ divides it.
§Worst-case complexity
$T(n) = O(n)$
$M(n) = O(n)$
where $T$ is time, $M$ is additional memory, and $n$ is self.significant_bits().
§Examples
use malachite_base::num::basic::traits::Two;
use malachite_nz::gaussian_integer::GaussianInteger;
use std::str::FromStr;
// 6+2i = (-1-2i)(1+i)^3
let (q, k) = GaussianInteger::from_str("6+2i")
.unwrap()
.remove_one_plus_i();
assert_eq!(q.to_string(), "-1-2i");
assert_eq!(k, 3);
// 2 = (-i)(1+i)^2
let (q, k) = GaussianInteger::TWO.remove_one_plus_i();
assert_eq!(q.to_string(), "-i");
assert_eq!(k, 2);
// 3+2i is not divisible by 1+i
let (q, k) = GaussianInteger::from_str("3+2i")
.unwrap()
.remove_one_plus_i();
assert_eq!(q.to_string(), "3+2i");
assert_eq!(k, 0);Sourcepub fn max_significant_bits(&self) -> u64
pub fn max_significant_bits(&self) -> u64
Returns the larger of the numbers of significant bits of the real and imaginary parts of a
GaussianInteger, each taken in absolute value.
This is the size measure that FLINT’s fmpzi_bits computes, and the one that the sizes of
the parts are compared against when an algorithm is chosen; the SignificantBits
implementation sums the two counts instead.
$$ f(a + bi) = \max(\operatorname{bits}(a), \operatorname{bits}(b)), $$ where $\operatorname{bits}(n)$ is the number of significant bits of $|n|$, with $\operatorname{bits}(0) = 0$.
§Worst-case complexity
Constant time and additional memory.
§Examples
use malachite_base::num::basic::traits::Zero;
use malachite_nz::gaussian_integer::GaussianInteger;
use std::str::FromStr;
assert_eq!(GaussianInteger::ZERO.max_significant_bits(), 0);
assert_eq!(
GaussianInteger::from_str("3+4i")
.unwrap()
.max_significant_bits(),
3
);
assert_eq!(
GaussianInteger::from_str("1000000000000+i")
.unwrap()
.max_significant_bits(),
40
);Trait Implementations§
Source§impl Clone for ComparableGaussianInteger
impl Clone for ComparableGaussianInteger
Source§impl Debug for ComparableGaussianInteger
impl Debug for ComparableGaussianInteger
Source§impl Deref for ComparableGaussianInteger
impl Deref for ComparableGaussianInteger
Source§fn deref(&self) -> &GaussianInteger
fn deref(&self) -> &GaussianInteger
Allows a ComparableGaussianInteger to dereference to a GaussianInteger.
use malachite_base::num::basic::traits::One;
use malachite_nz::gaussian_integer::{ComparableGaussianInteger, GaussianInteger};
let x = ComparableGaussianInteger(GaussianInteger::ONE);
assert_eq!(*x, GaussianInteger::ONE);Source§type Target = GaussianInteger
type Target = GaussianInteger
Source§impl Display for ComparableGaussianInteger
impl Display for ComparableGaussianInteger
Source§fn fmt(&self, f: &mut Formatter<'_>) -> Result
fn fmt(&self, f: &mut Formatter<'_>) -> Result
Converts a ComparableGaussianInteger to a String, writing the wrapped
GaussianInteger exactly as its own Display implementation does.
§Worst-case complexity
$T(n) = O(n (\log n)^2 \log\log n)$
$M(n) = O(n \log n)$
where $T$ is time, $M$ is additional memory, and $n$ is the maximum number of significant bits of the real and imaginary parts.
§Examples
use malachite_base::num::basic::traits::I;
use malachite_nz::gaussian_integer::{ComparableGaussianInteger, GaussianInteger};
assert_eq!(
ComparableGaussianInteger(GaussianInteger::I).to_string(),
"i"
);impl Eq for ComparableGaussianInteger
Source§impl Hash for ComparableGaussianInteger
impl Hash for ComparableGaussianInteger
Source§impl Ord for ComparableGaussianInteger
impl Ord for ComparableGaussianInteger
Source§fn cmp(&self, other: &Self) -> Ordering
fn cmp(&self, other: &Self) -> Ordering
Compares two ComparableGaussianIntegers.
The order is lexicographic: real parts are compared first, and imaginary parts break ties.
This is a total order, and its equality agrees with
GaussianInteger equality, but it is not
compatible with arithmetic: no total order on the complex numbers is. It is intended for
canonically sorting Gaussian integers and for using them as keys in ordered collections.
§Worst-case complexity
$T(n) = O(n)$
$M(n) = O(1)$
where $T$ is time, $M$ is additional memory, and $n$ is the maximum number of significant
bits of the real and imaginary parts of self and other.
§Examples
use malachite_base::num::basic::traits::{I, NegativeI, One, Zero};
use malachite_nz::gaussian_integer::{ComparableGaussianInteger, GaussianInteger};
// 0 < i, since the real parts are equal and 0 < 1
assert!(
ComparableGaussianInteger(GaussianInteger::ZERO)
< ComparableGaussianInteger(GaussianInteger::I)
);
// -i < i
assert!(
ComparableGaussianInteger(GaussianInteger::NEGATIVE_I)
< ComparableGaussianInteger(GaussianInteger::I)
);
// i < 1, since 0 < 1 and the real parts are compared first
assert!(
ComparableGaussianInteger(GaussianInteger::I)
< ComparableGaussianInteger(GaussianInteger::ONE)
);1.21.0 (const: unstable) · Source§fn max(self, other: Self) -> Selfwhere
Self: Sized,
fn max(self, other: Self) -> Selfwhere
Self: Sized,
1.21.0 (const: unstable) · Source§fn min(self, other: Self) -> Selfwhere
Self: Sized,
fn min(self, other: Self) -> Selfwhere
Self: Sized,
Source§impl PartialOrd for ComparableGaussianInteger
impl PartialOrd for ComparableGaussianInteger
Source§fn partial_cmp(&self, other: &Self) -> Option<Ordering>
fn partial_cmp(&self, other: &Self) -> Option<Ordering>
Compares two ComparableGaussianIntegers.
See the documentation for the Ord implementation.
impl StructuralPartialEq for ComparableGaussianInteger
Source§impl ToLatex for ComparableGaussianInteger
impl ToLatex for ComparableGaussianInteger
Source§fn fmt_latex(&self, f: &mut Formatter<'_>) -> Result
fn fmt_latex(&self, f: &mut Formatter<'_>) -> Result
Writes a ComparableGaussianInteger as a LaTeX math-mode fragment.
The fragment is the wrapped GaussianInteger’s own: the wrapper exists to give an
ordering, and does not change what the value is.
§Worst-case complexity
Same as the time and additional memory complexity of fmt_latex for GaussianInteger.
§Examples
use malachite_base::strings::latex::ToLatex;
use malachite_nz::gaussian_integer::{ComparableGaussianInteger, GaussianInteger};
let x = GaussianInteger::from(2);
assert_eq!(
ComparableGaussianInteger(x.clone()).to_latex_string(),
x.to_latex_string()
);Source§impl ToTypst for ComparableGaussianInteger
impl ToTypst for ComparableGaussianInteger
Source§fn fmt_typst(&self, f: &mut Formatter<'_>) -> Result
fn fmt_typst(&self, f: &mut Formatter<'_>) -> Result
Writes a ComparableGaussianInteger as a Typst math-mode fragment.
The fragment is the wrapped GaussianInteger’s own: the wrapper exists to give an
ordering, and does not change what the value is.
§Worst-case complexity
Same as the time and additional memory complexity of fmt_typst for GaussianInteger.
§Examples
use malachite_base::strings::typst::ToTypst;
use malachite_nz::gaussian_integer::{ComparableGaussianInteger, GaussianInteger};
let x = GaussianInteger::from(2);
assert_eq!(
ComparableGaussianInteger(x.clone()).to_typst_string(),
x.to_typst_string()
);Auto Trait Implementations§
impl Freeze for ComparableGaussianInteger
impl RefUnwindSafe for ComparableGaussianInteger
impl Send for ComparableGaussianInteger
impl Sync for ComparableGaussianInteger
impl Unpin for ComparableGaussianInteger
impl UnsafeUnpin for ComparableGaussianInteger
impl UnwindSafe for ComparableGaussianInteger
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
impl<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
Source§impl<T, U> ImaginaryInto<U> for Twhere
U: ImaginaryFrom<T>,
impl<T, U> ImaginaryInto<U> for Twhere
U: ImaginaryFrom<T>,
fn imaginary_into(self) -> U
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more