malachite_float/arithmetic/mod.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
9/// Absolute value of [`Float`](super::Float)s.
10pub mod abs;
11/// Addition of [`Float`](super::Float)s, and of [`Float`](super::Float)s with
12/// [`Rational`](malachite_q::Rational)s.
13pub mod add;
14/// Division of [`Float`](super::Float)s, of [`Float`](super::Float)s by
15/// [`Rational`](malachite_q::Rational)s, and of [`Rational`](malachite_q::Rational)s by
16/// [`Float`](super::Float)s.
17pub mod div;
18/// An implementations of [`IsPowerOf2`](malachite_base::num::arithmetic::traits::IsPowerOf2), a
19/// trait for determining whether a number is an integer power of 2.
20pub mod is_power_of_2;
21/// Multiplication of [`Float`](super::Float)s, and of [`Float`](super::Float)s with
22/// [`Rational`](malachite_q::Rational)s.
23pub mod mul;
24/// Negation of [`Float`](super::Float)s.
25pub mod neg;
26/// Implementations of [`PowerOf2`](malachite_base::num::arithmetic::traits::PowerOf2), a trait for
27/// computing a power of 2.
28pub mod power_of_2;
29/// Implementations of [`Reciprocal`](malachite_base::num::arithmetic::traits::Reciprocal) and
30/// [`ReciprocalAssign`](malachite_base::num::arithmetic::traits::ReciprocalAssign), traits for
31/// computing the reciprocal of a number.
32pub mod reciprocal;
33/// Left-shifting a [`Float`](super::Float) (multiplying it by a power of 2).
34///
35/// # shl
36/// ```
37/// use malachite_base::num::basic::traits::{Infinity, Zero};
38/// use malachite_float::Float;
39///
40/// assert_eq!(Float::ZERO << 10, 0);
41/// assert_eq!(Float::INFINITY << 10, Float::INFINITY);
42/// assert_eq!(
43/// (Float::from(std::f64::consts::PI) << 10u8).to_string(),
44/// "3216.990877275948"
45/// );
46/// assert_eq!(
47/// (Float::from(std::f64::consts::PI) << -10i8).to_string(),
48/// "0.003067961575771282"
49/// );
50///
51/// assert_eq!(&Float::ZERO << 10, 0);
52/// assert_eq!(&Float::INFINITY << 10, Float::INFINITY);
53/// assert_eq!(
54/// (&Float::from(std::f64::consts::PI) << 10u8).to_string(),
55/// "3216.990877275948"
56/// );
57/// assert_eq!(
58/// (&Float::from(std::f64::consts::PI) << -10i8).to_string(),
59/// "0.003067961575771282"
60/// );
61/// ```
62///
63/// # shl_assign
64/// ```
65/// use malachite_base::num::basic::traits::{Infinity, Zero};
66/// use malachite_float::Float;
67///
68/// let mut x = Float::ZERO;
69/// x <<= 10;
70/// assert_eq!(x, 0);
71///
72/// let mut x = Float::INFINITY;
73/// x <<= 10;
74/// assert_eq!(x, Float::INFINITY);
75///
76/// let mut x = Float::from(std::f64::consts::PI);
77/// x <<= 10;
78/// assert_eq!(x.to_string(), "3216.990877275948");
79///
80/// let mut x = Float::from(std::f64::consts::PI);
81/// x <<= -10;
82/// assert_eq!(x.to_string(), "0.003067961575771282");
83/// ```
84pub mod shl;
85/// Implementations of [`ShlRound`](malachite_base::num::arithmetic::traits::ShlRound) and
86/// [`ShlRoundAssign`](malachite_base::num::arithmetic::traits::ShlRoundAssign), traits for
87/// multiplying a number by a power of 2 and rounding according to a specified
88/// [`RoundingMode`](malachite_base::rounding_modes::RoundingMode). For [`Float`](super::Float)s,
89/// rounding is only necessary in the cases of overflow and underflow.
90///
91/// # shl_prec_round
92/// ```
93/// use malachite_base::rounding_modes::RoundingMode::*;
94/// use malachite_float::Float;
95/// use std::cmp::Ordering::*;
96///
97/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round(10u8, 10, Nearest);
98/// assert_eq!(shifted.to_string(), "3216.0");
99/// assert_eq!(o, Less);
100///
101/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round(-10i8, 10, Nearest);
102/// assert_eq!(shifted.to_string(), "0.003067");
103/// assert_eq!(o, Less);
104///
105/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round(u32::MAX, 10, Floor);
106/// assert_eq!(shifted.to_string(), "too_big");
107/// assert_eq!(o, Less);
108///
109/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round(u32::MAX, 10, Ceiling);
110/// assert_eq!(shifted.to_string(), "Infinity");
111/// assert_eq!(o, Greater);
112///
113/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round_ref(10u8, 10, Nearest);
114/// assert_eq!(shifted.to_string(), "3216.0");
115/// assert_eq!(o, Less);
116///
117/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round_ref(-10i8, 10, Nearest);
118/// assert_eq!(shifted.to_string(), "0.003067");
119/// assert_eq!(o, Less);
120///
121/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round_ref(u32::MAX, 10, Floor);
122/// assert_eq!(shifted.to_string(), "too_big");
123/// assert_eq!(o, Less);
124///
125/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_round_ref(u32::MAX, 10, Ceiling);
126/// assert_eq!(shifted.to_string(), "Infinity");
127/// assert_eq!(o, Greater);
128/// ```
129///
130/// # shl_prec_round_assign
131/// ```
132/// use malachite_base::rounding_modes::RoundingMode::*;
133/// use malachite_float::Float;
134/// use std::cmp::Ordering::*;
135///
136/// let mut x = Float::from(std::f64::consts::PI);
137/// assert_eq!(x.shl_prec_round_assign(10u8, 10, Nearest), Less);
138/// assert_eq!(x.to_string(), "3216.0");
139///
140/// let mut x = Float::from(std::f64::consts::PI);
141/// assert_eq!(x.shl_prec_round_assign(-10i8, 10, Nearest), Less);
142/// assert_eq!(x.to_string(), "0.003067");
143///
144/// let mut x = Float::from(std::f64::consts::PI);
145/// assert_eq!(x.shl_prec_round_assign(u32::MAX, 10, Floor), Less);
146/// assert_eq!(x.to_string(), "too_big");
147///
148/// let mut x = Float::from(std::f64::consts::PI);
149/// assert_eq!(x.shl_prec_round_assign(u32::MAX, 10, Ceiling), Greater);
150/// assert_eq!(x.to_string(), "Infinity");
151/// ```
152///
153/// # shl_prec
154/// ```
155/// use malachite_float::Float;
156/// use std::cmp::Ordering::*;
157///
158/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec(10u8, 10);
159/// assert_eq!(shifted.to_string(), "3216.0");
160/// assert_eq!(o, Less);
161///
162/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec(-10i8, 10);
163/// assert_eq!(shifted.to_string(), "0.003067");
164/// assert_eq!(o, Less);
165///
166/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec(u32::MAX, 10);
167/// assert_eq!(shifted.to_string(), "Infinity");
168/// assert_eq!(o, Greater);
169///
170/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_ref(10u8, 10);
171/// assert_eq!(shifted.to_string(), "3216.0");
172/// assert_eq!(o, Less);
173///
174/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_ref(-10i8, 10);
175/// assert_eq!(shifted.to_string(), "0.003067");
176/// assert_eq!(o, Less);
177///
178/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_prec_ref(u32::MAX, 10);
179/// assert_eq!(shifted.to_string(), "Infinity");
180/// assert_eq!(o, Greater);
181/// ```
182///
183/// # shl_prec_assign
184/// ```
185/// use malachite_float::Float;
186/// use std::cmp::Ordering::*;
187///
188/// let mut x = Float::from(std::f64::consts::PI);
189/// assert_eq!(x.shl_prec_assign(10u8, 10), Less);
190/// assert_eq!(x.to_string(), "3216.0");
191///
192/// let mut x = Float::from(std::f64::consts::PI);
193/// assert_eq!(x.shl_prec_assign(-10i8, 10), Less);
194/// assert_eq!(x.to_string(), "0.003067");
195///
196/// let mut x = Float::from(std::f64::consts::PI);
197/// assert_eq!(x.shl_prec_assign(u32::MAX, 10), Greater);
198/// assert_eq!(x.to_string(), "Infinity");
199/// ```
200///
201/// # shl_round
202/// ```
203/// use malachite_base::num::arithmetic::traits::ShlRound;
204/// use malachite_base::rounding_modes::RoundingMode::*;
205/// use malachite_float::Float;
206/// use std::cmp::Ordering::*;
207///
208/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_round(10u8, Nearest);
209/// assert_eq!(shifted.to_string(), "3216.990877275948");
210/// assert_eq!(o, Equal);
211///
212/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_round(-10i8, Nearest);
213/// assert_eq!(shifted.to_string(), "0.003067961575771282");
214/// assert_eq!(o, Equal);
215///
216/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_round(u32::MAX, Floor);
217/// assert_eq!(shifted.to_string(), "too_big");
218/// assert_eq!(o, Less);
219///
220/// let (shifted, o) = Float::from(std::f64::consts::PI).shl_round(u32::MAX, Ceiling);
221/// assert_eq!(shifted.to_string(), "Infinity");
222/// assert_eq!(o, Greater);
223///
224/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shl_round(10u8, Nearest);
225/// assert_eq!(shifted.to_string(), "3216.990877275948");
226/// assert_eq!(o, Equal);
227///
228/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shl_round(-10i8, Nearest);
229/// assert_eq!(shifted.to_string(), "0.003067961575771282");
230/// assert_eq!(o, Equal);
231///
232/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shl_round(u32::MAX, Floor);
233/// assert_eq!(shifted.to_string(), "too_big");
234/// assert_eq!(o, Less);
235///
236/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shl_round(u32::MAX, Ceiling);
237/// assert_eq!(shifted.to_string(), "Infinity");
238/// assert_eq!(o, Greater);
239/// ```
240///
241/// # shl_round_assign
242/// ```
243/// use malachite_base::num::arithmetic::traits::ShlRoundAssign;
244/// use malachite_base::rounding_modes::RoundingMode::*;
245/// use malachite_float::Float;
246/// use std::cmp::Ordering::*;
247///
248/// let mut x = Float::from(std::f64::consts::PI);
249/// assert_eq!(x.shl_round_assign(10u8, Nearest), Equal);
250/// assert_eq!(x.to_string(), "3216.990877275948");
251///
252/// let mut x = Float::from(std::f64::consts::PI);
253/// assert_eq!(x.shl_round_assign(-10i8, Nearest), Equal);
254/// assert_eq!(x.to_string(), "0.003067961575771282");
255///
256/// let mut x = Float::from(std::f64::consts::PI);
257/// assert_eq!(x.shl_round_assign(u32::MAX, Floor), Less);
258/// assert_eq!(x.to_string(), "too_big");
259///
260/// let mut x = Float::from(std::f64::consts::PI);
261/// assert_eq!(x.shl_round_assign(u32::MAX, Ceiling), Greater);
262/// assert_eq!(x.to_string(), "Infinity");
263/// ```
264pub mod shl_round;
265/// Right-shifting a [`Float`](super::Float) (dividing it by a power of 2).
266///
267/// # shr
268/// ```
269/// use malachite_base::num::basic::traits::{Infinity, Zero};
270/// use malachite_float::Float;
271///
272/// assert_eq!(Float::ZERO >> 10, 0);
273/// assert_eq!(Float::INFINITY >> 10, Float::INFINITY);
274/// assert_eq!(
275/// (Float::from(std::f64::consts::PI) >> 10u8).to_string(),
276/// "0.003067961575771282"
277/// );
278/// assert_eq!(
279/// (Float::from(std::f64::consts::PI) >> -10i8).to_string(),
280/// "3216.990877275948"
281/// );
282///
283/// assert_eq!(&Float::ZERO >> 10, 0);
284/// assert_eq!(&Float::INFINITY >> 10, Float::INFINITY);
285/// assert_eq!(
286/// (&Float::from(std::f64::consts::PI) >> 10u8).to_string(),
287/// "0.003067961575771282"
288/// );
289/// assert_eq!(
290/// (&Float::from(std::f64::consts::PI) >> -10i8).to_string(),
291/// "3216.990877275948"
292/// );
293/// ```
294///
295/// # shr_assign
296/// ```
297/// use malachite_base::num::basic::traits::{Infinity, Zero};
298/// use malachite_float::Float;
299///
300/// let mut x = Float::ZERO;
301/// x >>= 10;
302/// assert_eq!(x, 0);
303///
304/// let mut x = Float::INFINITY;
305/// x >>= 10;
306/// assert_eq!(x, Float::INFINITY);
307///
308/// let mut x = Float::from(std::f64::consts::PI);
309/// x >>= 10;
310/// assert_eq!(x.to_string(), "0.003067961575771282");
311///
312/// let mut x = Float::from(std::f64::consts::PI);
313/// x >>= -10;
314/// assert_eq!(x.to_string(), "3216.990877275948");
315/// ```
316pub mod shr;
317/// Implementations of [`ShlRound`](malachite_base::num::arithmetic::traits::ShrRound) and
318/// [`ShrRoundAssign`](malachite_base::num::arithmetic::traits::ShrRoundAssign), traits for dividing
319/// a number by a power of 2 and rounding according to a specified
320/// [`RoundingMode`](malachite_base::rounding_modes::RoundingMode). For [`Float`](super::Float)s,
321/// rounding is only necessary in the cases of overflow and underflow.
322///
323/// # shr_prec_round
324/// ```
325/// use malachite_base::rounding_modes::RoundingMode::*;
326/// use malachite_float::Float;
327/// use std::cmp::Ordering::*;
328///
329/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round(10u8, 10, Nearest);
330/// assert_eq!(shifted.to_string(), "0.003067");
331/// assert_eq!(o, Less);
332///
333/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round(-10i8, 10, Nearest);
334/// assert_eq!(shifted.to_string(), "3216.0");
335/// assert_eq!(o, Less);
336///
337/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round(u32::MAX, 10, Floor);
338/// assert_eq!(shifted.to_string(), "0.0");
339/// assert_eq!(o, Less);
340///
341/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round(u32::MAX, 10, Ceiling);
342/// assert_eq!(shifted.to_string(), "too_small");
343/// assert_eq!(o, Greater);
344///
345/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round_ref(10u8, 10, Nearest);
346/// assert_eq!(shifted.to_string(), "0.003067");
347/// assert_eq!(o, Less);
348///
349/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round_ref(-10i8, 10, Nearest);
350/// assert_eq!(shifted.to_string(), "3216.0");
351/// assert_eq!(o, Less);
352///
353/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round_ref(u32::MAX, 10, Floor);
354/// assert_eq!(shifted.to_string(), "0.0");
355/// assert_eq!(o, Less);
356///
357/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_round_ref(u32::MAX, 10, Ceiling);
358/// assert_eq!(shifted.to_string(), "too_small");
359/// assert_eq!(o, Greater);
360/// ```
361///
362/// # shr_prec_round_assign
363/// ```
364/// use malachite_base::rounding_modes::RoundingMode::*;
365/// use malachite_float::Float;
366/// use std::cmp::Ordering::*;
367///
368/// let mut x = Float::from(std::f64::consts::PI);
369/// assert_eq!(x.shr_prec_round_assign(10u8, 10, Nearest), Less);
370/// assert_eq!(x.to_string(), "0.003067");
371///
372/// let mut x = Float::from(std::f64::consts::PI);
373/// assert_eq!(x.shr_prec_round_assign(-10i8, 10, Nearest), Less);
374/// assert_eq!(x.to_string(), "3216.0");
375///
376/// let mut x = Float::from(std::f64::consts::PI);
377/// assert_eq!(x.shr_prec_round_assign(u32::MAX, 10, Floor), Less);
378/// assert_eq!(x.to_string(), "0.0");
379///
380/// let mut x = Float::from(std::f64::consts::PI);
381/// assert_eq!(x.shr_prec_round_assign(u32::MAX, 10, Ceiling), Greater);
382/// assert_eq!(x.to_string(), "too_small");
383/// ```
384///
385/// # shr_prec
386/// ```
387/// use malachite_float::Float;
388/// use std::cmp::Ordering::*;
389///
390/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec(10u8, 10);
391/// assert_eq!(shifted.to_string(), "0.003067");
392/// assert_eq!(o, Less);
393///
394/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec(-10i8, 10);
395/// assert_eq!(shifted.to_string(), "3216.0");
396/// assert_eq!(o, Less);
397///
398/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec(u32::MAX, 10);
399/// assert_eq!(shifted.to_string(), "0.0");
400/// assert_eq!(o, Less);
401///
402/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_ref(10u8, 10);
403/// assert_eq!(shifted.to_string(), "0.003067");
404/// assert_eq!(o, Less);
405///
406/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_ref(-10i8, 10);
407/// assert_eq!(shifted.to_string(), "3216.0");
408/// assert_eq!(o, Less);
409///
410/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_prec_ref(u32::MAX, 10);
411/// assert_eq!(shifted.to_string(), "0.0");
412/// assert_eq!(o, Less);
413/// ```
414///
415/// # shr_prec_assign
416/// ```
417/// use malachite_float::Float;
418/// use std::cmp::Ordering::*;
419///
420/// let mut x = Float::from(std::f64::consts::PI);
421/// assert_eq!(x.shr_prec_assign(10u8, 10), Less);
422/// assert_eq!(x.to_string(), "0.003067");
423///
424/// let mut x = Float::from(std::f64::consts::PI);
425/// assert_eq!(x.shr_prec_assign(-10i8, 10), Less);
426/// assert_eq!(x.to_string(), "3216.0");
427///
428/// let mut x = Float::from(std::f64::consts::PI);
429/// assert_eq!(x.shr_prec_assign(u32::MAX, 10), Less);
430/// assert_eq!(x.to_string(), "0.0");
431/// ```
432///
433/// # shr_round
434/// ```
435/// use malachite_base::num::arithmetic::traits::ShrRound;
436/// use malachite_base::rounding_modes::RoundingMode::*;
437/// use malachite_float::Float;
438/// use std::cmp::Ordering::*;
439///
440/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_round(10u8, Nearest);
441/// assert_eq!(shifted.to_string(), "0.003067961575771282");
442/// assert_eq!(o, Equal);
443///
444/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_round(-10i8, Nearest);
445/// assert_eq!(shifted.to_string(), "3216.990877275948");
446/// assert_eq!(o, Equal);
447///
448/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_round(u32::MAX, Floor);
449/// assert_eq!(shifted.to_string(), "0.0");
450/// assert_eq!(o, Less);
451///
452/// let (shifted, o) = Float::from(std::f64::consts::PI).shr_round(u32::MAX, Ceiling);
453/// assert_eq!(shifted.to_string(), "too_small");
454/// assert_eq!(o, Greater);
455///
456/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shr_round(10u8, Nearest);
457/// assert_eq!(shifted.to_string(), "0.003067961575771282");
458/// assert_eq!(o, Equal);
459///
460/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shr_round(-10i8, Nearest);
461/// assert_eq!(shifted.to_string(), "3216.990877275948");
462/// assert_eq!(o, Equal);
463///
464/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shr_round(u32::MAX, Floor);
465/// assert_eq!(shifted.to_string(), "0.0");
466/// assert_eq!(o, Less);
467///
468/// let (shifted, o) = (&Float::from(std::f64::consts::PI)).shr_round(u32::MAX, Ceiling);
469/// assert_eq!(shifted.to_string(), "too_small");
470/// assert_eq!(o, Greater);
471/// ```
472///
473/// # shr_round_assign
474/// ```
475/// use malachite_base::num::arithmetic::traits::ShrRoundAssign;
476/// use malachite_base::rounding_modes::RoundingMode::*;
477/// use malachite_float::Float;
478/// use std::cmp::Ordering::*;
479///
480/// let mut x = Float::from(std::f64::consts::PI);
481/// assert_eq!(x.shr_round_assign(10u8, Nearest), Equal);
482/// assert_eq!(x.to_string(), "0.003067961575771282");
483///
484/// let mut x = Float::from(std::f64::consts::PI);
485/// assert_eq!(x.shr_round_assign(-10i8, Nearest), Equal);
486/// assert_eq!(x.to_string(), "3216.990877275948");
487///
488/// let mut x = Float::from(std::f64::consts::PI);
489/// assert_eq!(x.shr_round_assign(u32::MAX, Floor), Less);
490/// assert_eq!(x.to_string(), "0.0");
491///
492/// let mut x = Float::from(std::f64::consts::PI);
493/// assert_eq!(x.shr_round_assign(u32::MAX, Ceiling), Greater);
494/// assert_eq!(x.to_string(), "too_small");
495/// ```
496pub mod shr_round;
497/// An implementation of [`Sign`](malachite_base::num::arithmetic::traits::Sign), a trait for
498/// determining the sign of a number.
499pub mod sign;
500/// Squaring of [`Float`](super::Float)s.
501pub mod square;
502/// Subtraction of [`Float`](super::Float)s, of [`Float`](super::Float)s by
503/// [`Rational`](malachite_q::Rational)s, and of [`Rational`](malachite_q::Rational)s by
504/// [`Float`](super::Float)s.
505pub mod sub;