malachite_q/comparison/eq_abs_primitive_float.rs
1// Copyright © 2025 Mikhail Hogrefe
2//
3// This file is part of Malachite.
4//
5// Malachite is free software: you can redistribute it and/or modify it under the terms of the GNU
6// Lesser General Public License (LGPL) as published by the Free Software Foundation; either version
7// 3 of the License, or (at your option) any later version. See <https://www.gnu.org/licenses/>.
8
9use crate::Rational;
10use malachite_base::num::arithmetic::traits::{FloorLogBase2, IsPowerOf2};
11use malachite_base::num::comparison::traits::EqAbs;
12use malachite_base::num::conversion::traits::ExactFrom;
13
14macro_rules! impl_eq_abs {
15 ($t: ident) => {
16 impl EqAbs<$t> for Rational {
17 /// Determines whether the absolute values of a [`Rational`] and a primitive float are
18 /// equal.
19 ///
20 /// # Worst-case complexity
21 /// $T(n) = O(n)$
22 ///
23 /// $M(m) = O(m)$
24 ///
25 /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
26 /// other.sci_exponent().abs())`, and $m$ is `other.sci_exponent().abs()`.
27 ///
28 /// See [here](super::eq_abs_primitive_float#eq_abs).
29 #[inline]
30 fn eq_abs(&self, other: &$t) -> bool {
31 if !other.is_finite() {
32 false
33 } else if *other == 0.0 {
34 *self == 0u32
35 } else {
36 *self != 0u32
37 && self.denominator.is_power_of_2()
38 && self.floor_log_base_2_abs() == other.abs().floor_log_base_2()
39 && self.eq_abs(&Rational::exact_from(other.abs()))
40 }
41 }
42 }
43
44 impl EqAbs<Rational> for $t {
45 /// Determines whether the absolute values of a primitive float and a [`Rational`] are
46 /// equal.
47 ///
48 /// # Worst-case complexity
49 /// $T(n) = O(n)$
50 ///
51 /// $M(m) = O(m)$
52 ///
53 /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.sci_exponent().abs(),
54 /// other.significant_bits())`, and $m$ is `self.sci_exponent().abs()`.
55 ///
56 /// See [here](super::eq_abs_primitive_float#eq_abs).
57 #[inline]
58 fn eq_abs(&self, other: &Rational) -> bool {
59 other.eq_abs(self)
60 }
61 }
62 };
63}
64apply_to_primitive_floats!(impl_eq_abs);