Skip to main content

malachite_nz/natural/comparison/
partial_eq_primitive_int.rs

1// Copyright © 2026 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::natural::InnerNatural::{Large, Small};
10use crate::natural::Natural;
11use crate::platform::Limb;
12use malachite_base::num::basic::integers::{PrimitiveInt, USIZE_IS_U32};
13use malachite_base::num::conversion::traits::WrappingFrom;
14
15macro_rules! impl_partial_eq_limb {
16    ($u: ident) => {
17        impl PartialEq<$u> for Natural {
18            /// Determines whether a [`Natural`] is equal to a [`Limb`](crate#limbs).
19            ///
20            /// # Worst-case complexity
21            /// Constant time and additional memory.
22            ///
23            /// # Examples
24            /// See [here](super::partial_eq_primitive_int#partial_eq).
25            fn eq(&self, other: &$u) -> bool {
26                match self {
27                    Natural(Small(x)) => *x == *other,
28                    Natural(Large(_)) => false,
29                }
30            }
31        }
32
33        impl PartialEq<Natural> for $u {
34            /// Determines whether a [`Limb`](crate#limbs) is equal to a [`Natural`].
35            ///
36            /// # Worst-case complexity
37            /// Constant time and additional memory.
38            ///
39            /// # Examples
40            /// See [here](super::partial_eq_primitive_int#partial_eq).
41            #[inline]
42            fn eq(&self, other: &Natural) -> bool {
43                other == self
44            }
45        }
46    };
47}
48
49macro_rules! impl_partial_eq_smaller_than_limb {
50    ($u: ident) => {
51        impl PartialEq<$u> for Natural {
52            /// Determines whether a [`Natural`] is equal to a value of an unsigned primitive
53            /// integer type that's smaller than a [`Limb`](crate#limbs).
54            ///
55            /// # Worst-case complexity
56            /// Constant time and additional memory.
57            ///
58            /// # Examples
59            /// See [here](super::partial_eq_primitive_int#partial_eq).
60            #[allow(clippy::cmp_owned)]
61            #[inline]
62            fn eq(&self, other: &$u) -> bool {
63                *self == Limb::from(*other)
64            }
65        }
66
67        impl PartialEq<Natural> for $u {
68            /// Determines whether a value of an unsigned primitive integer type that's smaller than
69            /// a [`Limb`](crate#limbs) is equal to a [`Natural`].
70            ///
71            /// # Worst-case complexity
72            /// Constant time and additional memory.
73            ///
74            /// # Examples
75            /// See [here](super::partial_eq_primitive_int#partial_eq).
76            #[allow(clippy::cmp_owned)]
77            #[inline]
78            fn eq(&self, other: &Natural) -> bool {
79                Limb::from(*self) == *other
80            }
81        }
82    };
83}
84
85macro_rules! impl_partial_eq_larger_than_limb_or_usize {
86    ($u: ident) => {
87        impl PartialEq<Natural> for $u {
88            /// Determines whether a value of an unsigned primitive integer type that's larger than
89            /// a [`Limb`](crate#limbs) is equal to a [`Natural`].
90            ///
91            /// This implementation is general enough to also work for [`usize`], regardless of
92            /// whether it is equal in width to [`Limb`](crate#limbs).
93            ///
94            /// # Worst-case complexity
95            /// Constant time and additional memory.
96            ///
97            /// # Examples
98            /// See [here](super::partial_eq_primitive_int#partial_eq).
99            #[inline]
100            fn eq(&self, other: &Natural) -> bool {
101                other == self
102            }
103        }
104    };
105}
106
107macro_rules! impl_partial_eq_larger_than_limb {
108    ($u: ident) => {
109        impl_partial_eq_larger_than_limb_or_usize!($u);
110
111        impl PartialEq<$u> for Natural {
112            /// Determines whether a [`Natural`] is equal to a value of an unsigned primitive
113            /// integer type that's larger than a [`Limb`](crate#limbs).
114            ///
115            /// # Worst-case complexity
116            /// Constant time and additional memory.
117            ///
118            /// # Examples
119            /// See [here](super::partial_eq_primitive_int#partial_eq).
120            #[inline]
121            fn eq(&self, other: &$u) -> bool {
122                let mut other = *other;
123                for limb in self.limbs() {
124                    if other == 0 || limb != Limb::wrapping_from(other) {
125                        return false;
126                    }
127                    other >>= Limb::WIDTH;
128                }
129                other == 0
130            }
131        }
132    };
133}
134
135macro_rules! impl_signed {
136    ($t: ident) => {
137        impl PartialEq<$t> for Natural {
138            /// Determines whether a [`Natural`] is equal to a signed primitive integer.
139            ///
140            /// # Worst-case complexity
141            /// Constant time and additional memory.
142            ///
143            /// # Examples
144            /// See [here](super::partial_eq_primitive_int#partial_eq).
145            fn eq(&self, other: &$t) -> bool {
146                *other >= 0 && *self == other.unsigned_abs()
147            }
148        }
149
150        impl PartialEq<Natural> for $t {
151            /// Determines whether a signed primitive integer is equal to a [`Natural`].
152            ///
153            /// # Worst-case complexity
154            /// Constant time and additional memory.
155            ///
156            /// # Examples
157            /// See [here](super::partial_eq_primitive_int#partial_eq).
158            #[inline]
159            fn eq(&self, other: &Natural) -> bool {
160                other == self
161            }
162        }
163    };
164}
165
166impl_partial_eq_smaller_than_limb!(u8);
167impl_partial_eq_smaller_than_limb!(u16);
168#[cfg(feature = "32_bit_limbs")]
169impl_partial_eq_limb!(u32);
170#[cfg(not(feature = "32_bit_limbs"))]
171impl_partial_eq_smaller_than_limb!(u32);
172#[cfg(feature = "32_bit_limbs")]
173impl_partial_eq_larger_than_limb!(u64);
174#[cfg(not(feature = "32_bit_limbs"))]
175impl_partial_eq_limb!(u64);
176impl_partial_eq_larger_than_limb!(u128);
177impl_partial_eq_larger_than_limb_or_usize!(usize);
178
179apply_to_signeds!(impl_signed);
180
181impl PartialEq<usize> for Natural {
182    /// Determines whether a [`Natural`] is equal to a [`usize`].
183    ///
184    /// # Worst-case complexity
185    /// Constant time and additional memory.
186    ///
187    /// See [here](super::partial_eq_primitive_int#partial_eq).
188    #[inline]
189    fn eq(&self, other: &usize) -> bool {
190        if USIZE_IS_U32 {
191            *self == u32::wrapping_from(*other)
192        } else {
193            assert_eq!(usize::WIDTH, u64::WIDTH);
194            *self == u64::wrapping_from(*other)
195        }
196    }
197}