Skip to main content

malachite_float/float/arithmetic/
agm.rs

1// Copyright © 2026 Mikhail Hogrefe
2//
3// Uses code adopted from the GNU MPFR Library.
4//
5//      Copyright 1999-2024 Free Software Foundation, Inc.
6//
7//      Contributed by the AriC and Caramba projects, INRIA.
8//
9// This file is part of Malachite.
10//
11// Malachite is free software: you can redistribute it and/or modify it under the terms of the GNU
12// Lesser General Public License (LGPL) as published by the Free Software Foundation; either version
13// 3 of the License, or (at your option) any later version. See <https://www.gnu.org/licenses/>.
14
15use crate::InnerFloat::{Finite, Infinity, NaN, Zero};
16use crate::float::basic::extended::{ExtendedFloat, agm_prec_round_normal_extended};
17use crate::{
18    Float, emulate_float_float_to_float_fn, emulate_rational_rational_to_float_fn,
19    float_either_infinity, float_either_zero, float_infinity, float_nan, float_zero,
20    floor_and_ceiling, test_overflow, test_underflow,
21};
22use alloc::borrow::Cow;
23use core::cmp::Ordering::{self, *};
24use core::cmp::max;
25use core::mem::swap;
26use malachite_base::num::arithmetic::traits::{
27    Agm, AgmAssign, CeilingLogBase2, ShrRoundAssign, Sign, Sqrt, SqrtAssign,
28};
29use malachite_base::num::basic::floats::PrimitiveFloat;
30use malachite_base::num::basic::integers::PrimitiveInt;
31use malachite_base::num::basic::traits::Zero as ZeroTrait;
32use malachite_base::num::conversion::traits::{ExactFrom, RoundingFrom, SaturatingFrom};
33use malachite_base::num::logic::traits::SignificantBits;
34use malachite_base::rounding_modes::RoundingMode::{self, *};
35use malachite_nz::natural::arithmetic::float_extras::float_can_round;
36use malachite_nz::natural::arithmetic::float_sub::exponent_shift_compare;
37use malachite_nz::platform::Limb;
38use malachite_q::Rational;
39
40// This is mpfr_cmp2 from cmp2.c, MPFR 4.3.0.
41fn cmp2_helper(b: &Float, c: &Float, cancel: &mut u64) -> Ordering {
42    match (b, c) {
43        (
44            Float(Finite {
45                exponent: x_exp,
46                precision: x_prec,
47                significand: x,
48                ..
49            }),
50            Float(Finite {
51                exponent: y_exp,
52                precision: y_prec,
53                significand: y,
54                ..
55            }),
56        ) => {
57            let (o, c) = exponent_shift_compare(
58                x.as_limbs_asc(),
59                i64::from(*x_exp),
60                *x_prec,
61                y.as_limbs_asc(),
62                i64::from(*y_exp),
63                *y_prec,
64            );
65            *cancel = c;
66            o
67        }
68        _ => panic!(),
69    }
70}
71
72// The exponent-scaling divisions below halve signed exponents with truncation toward zero, faithful
73// to MPFR's agm.c and to the bound proofs in the comments; `>>` (floor) would not preserve them.
74#[cfg_attr(dylint_lib = "malachite_lints", allow(mul_div_by_power_of_2_literal))]
75fn agm_prec_round_normal(
76    mut a: Float,
77    mut b: Float,
78    prec: u64,
79    rm: RoundingMode,
80) -> (Float, Ordering) {
81    if a < 0u32 || b < 0u32 {
82        return (float_nan!(), Equal);
83    }
84    let mut working_prec = prec + prec.ceiling_log_base_2() + 15;
85    // b (op2) and a (op1) are the 2 operands but we want b >= a
86    match a.partial_cmp(&b).unwrap() {
87        Equal => return Float::from_float_prec_round(a, prec, rm),
88        Greater => swap(&mut a, &mut b),
89        _ => {}
90    }
91    let mut scaleop = 0;
92    let mut increment = Limb::WIDTH;
93    let mut v;
94    let mut scaleit;
95    loop {
96        let mut err: u64 = 0;
97        let mut u;
98        loop {
99            let u_o;
100            let v_o;
101            (u, u_o) = a.mul_prec_ref_ref(&b, working_prec);
102            (v, v_o) = a.add_prec_ref_ref(&b, working_prec);
103            let u_overflow = test_overflow(&u, u_o);
104            let v_overflow = test_overflow(&v, v_o);
105            if u_overflow || v_overflow || test_underflow(&u, u_o) || test_underflow(&v, v_o) {
106                assert_eq!(scaleop, 0);
107                let e1 = a.get_exponent().unwrap();
108                let e2 = b.get_exponent().unwrap();
109                if u_overflow || v_overflow {
110                    // Let's recall that emin <= e1 <= e2 <= emax. There has been an overflow. Thus
111                    // e2 >= emax/2. If the mpfr_mul overflowed, then e1 + e2 > emax. If the
112                    // mpfr_add overflowed, then e2 = emax. We want: (e1 + scale) + (e2 + scale) <=
113                    // emax, i.e. scale <= (emax - e1 - e2) / 2. Let's take scale = min(floor((emax
114                    // - e1 - e2) / 2), -1). This is OK, as:
115                    // ```
116                    // - emin <= scale <= -1.
117                    // - e1 + scale >= emin. Indeed:
118                    //    * If e1 + e2 > emax, then
119                    //      e1 + scale >= e1 + (emax - e1 - e2) / 2 - 1
120                    //                 >= (emax + e1 - emax) / 2 - 1
121                    //                 >= e1 / 2 - 1 >= emin.
122                    //    * Otherwise, mpfr_mul didn't overflow, therefore
123                    //      mpfr_add overflowed and e2 = emax, so that
124                    //      e1 > emin (see restriction below).
125                    //      e1 + scale > emin - 1, thus e1 + scale >= emin.
126                    // - e2 + scale <= emax, since scale < 0.
127                    // ```
128                    let e_agm = e1 + e2;
129                    if e_agm > Float::MAX_EXPONENT {
130                        scaleop = -((e_agm - Float::MAX_EXPONENT + 1) / 2);
131                        assert!(scaleop < 0);
132                    } else {
133                        // The addition necessarily overflowed.
134                        assert_eq!(e2, Float::MAX_EXPONENT);
135                        // The case where e1 = emin and e2 = emax is not supported here. This would
136                        // mean that the precision of e2 would be huge (and possibly not supported
137                        // in practice anyway).
138                        assert!(e1 > Float::MIN_EXPONENT);
139                        // Note: this case is probably impossible to have in practice since we need
140                        // e2 = emax, and no overflow in the product. Since the product is >=
141                        // 2^(e1+e2-2), it implies e1 + e2 - 2 <= emax, thus e1 <= 2. Now to get an
142                        // overflow we need op1 >= 1/2 ulp(op2), which implies that the precision of
143                        // op2 should be at least emax-2. On a 64-bit computer this is impossible to
144                        // have, and would require a huge amount of memory on a 32-bit computer.
145                        scaleop = -1;
146                    }
147                } else {
148                    // underflow only (in the multiplication)
149                    //
150                    // We have e1 + e2 <= emin (so, e1 <= e2 <= 0). We want: (e1 + scale) + (e2 +
151                    // scale) >= emin + 1, i.e. scale >= (emin + 1 - e1 - e2) / 2. let's take scale
152                    // = ceil((emin + 1 - e1 - e2) / 2). This is OK, as: 1. 1 <= scale <= emax. 2.
153                    // e1 + scale >= emin + 1 >= emin. 3. e2 + scale <= scale <= emax.
154                    assert!(e1 <= e2 && e2 <= 0);
155                    scaleop = (Float::MIN_EXPONENT_PLUS_2 - e1 - e2) / 2;
156                    assert!(scaleop > 0);
157                }
158                a <<= scaleop;
159                b <<= scaleop;
160            } else {
161                break;
162            }
163        }
164        u.sqrt_assign();
165        v >>= 1u32;
166        scaleit = 0;
167        let mut n: u64 = 1;
168        let mut eq = 0;
169        'mid: while cmp2_helper(&u, &v, &mut eq) != Equal && eq <= working_prec - 2 {
170            let mut uf;
171            let mut vf;
172            loop {
173                vf = (&u + &v) >> 1;
174                // See proof in algorithms.tex
175                if eq > working_prec >> 2 {
176                    // vf = V(k)
177                    let low_p = (working_prec + 1) >> 1;
178                    let (mut w, o) = v.sub_prec_ref_ref(&u, low_p); // e = V(k-1)-U(k-1)
179                    let mut underflow = test_underflow(&w, o);
180                    let o = w.square_round_assign(Nearest); // e = e^2
181                    underflow |= test_underflow(&w, o);
182                    let o = w.shr_round_assign(4, Nearest); // e*= (1/2)^2*1/4
183                    underflow |= test_underflow(&w, o);
184                    let o = w.div_prec_assign_ref(&vf, low_p); // 1/4*e^2/V(k)
185                    underflow |= test_underflow(&w, o);
186                    let vf_exp = vf.get_exponent().unwrap();
187                    if !underflow {
188                        v = vf.sub_prec(w, working_prec).0;
189                        // 0 or 1
190                        err = u64::exact_from(vf_exp - v.get_exponent().unwrap());
191                        break 'mid;
192                    }
193                    // There has been an underflow because of the cancellation between V(k-1) and
194                    // U(k-1). Let's use the conventional method.
195                }
196                // U(k) increases, so that U.V can overflow (but not underflow).
197                uf = &u * &v;
198                // For multiplication using Nearest, is_infinite is sufficient for overflow checking
199                if uf.is_infinite() {
200                    let scale2 = -(((u.get_exponent().unwrap() + v.get_exponent().unwrap())
201                        - Float::MAX_EXPONENT
202                        + 1)
203                        / 2);
204                    u <<= scale2;
205                    v <<= scale2;
206                    scaleit += scale2;
207                } else {
208                    break;
209                }
210            }
211            u = uf.sqrt();
212            swap(&mut v, &mut vf);
213            n += 1;
214        }
215        // the error on v is bounded by (18n+51) ulps, or twice if there was an exponent loss in the
216        // final subtraction
217        //
218        // 18n+51 should not overflow since n is about log(p)
219        err += (18 * n + 51).ceiling_log_base_2();
220        // we should have n+2 <= 2^(p/4) [see algorithms.tex]
221        if (n + 2).ceiling_log_base_2() <= working_prec >> 2
222            && float_can_round(v.significand_ref().unwrap(), working_prec - err, prec, rm)
223        {
224            break;
225        }
226        working_prec += increment;
227        increment = working_prec >> 1;
228    }
229    v.shr_prec_round(scaleop + scaleit, prec, rm)
230}
231
232// See `agm_prec_round_normal`: the signed exponent halving truncates toward zero on purpose.
233#[cfg_attr(dylint_lib = "malachite_lints", allow(mul_div_by_power_of_2_literal))]
234fn agm_prec_round_ref_ref_normal(
235    a: &Float,
236    b: &Float,
237    prec: u64,
238    rm: RoundingMode,
239) -> (Float, Ordering) {
240    if *a < 0u32 || *b < 0u32 {
241        return (float_nan!(), Equal);
242    }
243    let mut working_prec = prec + prec.ceiling_log_base_2() + 15;
244    let mut a = Cow::Borrowed(a);
245    let mut b = Cow::Borrowed(b);
246    // b (op2) and a (op1) are the 2 operands but we want b >= a
247    match a.partial_cmp(&b).unwrap() {
248        Equal => return Float::from_float_prec_round_ref(a.as_ref(), prec, rm),
249        Greater => swap(&mut a, &mut b),
250        _ => {}
251    }
252    let mut scaleop = 0;
253    let mut increment = Limb::WIDTH;
254    let mut v;
255    let mut scaleit;
256    loop {
257        let mut err: u64 = 0;
258        let mut u;
259        loop {
260            let u_o;
261            let v_o;
262            (u, u_o) = a.mul_prec_ref_ref(&b, working_prec);
263            (v, v_o) = a.add_prec_ref_ref(&b, working_prec);
264            let u_overflow = test_overflow(&u, u_o);
265            let v_overflow = test_overflow(&v, v_o);
266            if u_overflow || v_overflow || test_underflow(&u, u_o) || test_underflow(&v, v_o) {
267                assert_eq!(scaleop, 0);
268                let e1 = a.get_exponent().unwrap();
269                let e2 = b.get_exponent().unwrap();
270                if u_overflow || v_overflow {
271                    // Let's recall that emin <= e1 <= e2 <= emax. There has been an overflow. Thus
272                    // e2 >= emax/2. If the mpfr_mul overflowed, then e1 + e2 > emax. If the
273                    // mpfr_add overflowed, then e2 = emax. We want: (e1 + scale) + (e2 + scale) <=
274                    // emax, i.e. scale <= (emax - e1 - e2) / 2. Let's take scale = min(floor((emax
275                    // - e1 - e2) / 2), -1). This is OK, as:
276                    // ```
277                    // - emin <= scale <= -1.
278                    // - e1 + scale >= emin. Indeed:
279                    //    * If e1 + e2 > emax, then
280                    //      e1 + scale >= e1 + (emax - e1 - e2) / 2 - 1
281                    //                 >= (emax + e1 - emax) / 2 - 1
282                    //                 >= e1 / 2 - 1 >= emin.
283                    //    * Otherwise, mpfr_mul didn't overflow, therefore
284                    //      mpfr_add overflowed and e2 = emax, so that
285                    //      e1 > emin (see restriction below).
286                    //      e1 + scale > emin - 1, thus e1 + scale >= emin.
287                    // - e2 + scale <= emax, since scale < 0.
288                    // ```
289                    let e_agm = e1 + e2;
290                    if e_agm > Float::MAX_EXPONENT {
291                        scaleop = -((e_agm - Float::MAX_EXPONENT + 1) / 2);
292                        assert!(scaleop < 0);
293                    } else {
294                        // The addition necessarily overflowed.
295                        assert_eq!(e2, Float::MAX_EXPONENT);
296                        // The case where e1 = emin and e2 = emax is not supported here. This would
297                        // mean that the precision of e2 would be huge (and possibly not supported
298                        // in practice anyway).
299                        assert!(e1 > Float::MIN_EXPONENT);
300                        // Note: this case is probably impossible to have in practice since we need
301                        // e2 = emax, and no overflow in the product. Since the product is >=
302                        // 2^(e1+e2-2), it implies e1 + e2 - 2 <= emax, thus e1 <= 2. Now to get an
303                        // overflow we need op1 >= 1/2 ulp(op2), which implies that the precision of
304                        // op2 should be at least emax-2. On a 64-bit computer this is impossible to
305                        // have, and would require a huge amount of memory on a 32-bit computer.
306                        scaleop = -1;
307                    }
308                } else {
309                    // underflow only (in the multiplication)
310                    //
311                    // We have e1 + e2 <= emin (so, e1 <= e2 <= 0). We want: (e1 + scale) + (e2 +
312                    // scale) >= emin + 1, i.e. scale >= (emin + 1 - e1 - e2) / 2. let's take scale
313                    // = ceil((emin + 1 - e1 - e2) / 2). This is OK, as: 1. 1 <= scale <= emax. 2.
314                    // e1 + scale >= emin + 1 >= emin. 3. e2 + scale <= scale <= emax.
315                    assert!(e1 <= e2 && e2 <= 0);
316                    scaleop = (Float::MIN_EXPONENT_PLUS_2 - e1 - e2) / 2;
317                    assert!(scaleop > 0);
318                }
319                *a.to_mut() <<= scaleop;
320                *b.to_mut() <<= scaleop;
321            } else {
322                break;
323            }
324        }
325        u.sqrt_assign();
326        v >>= 1u32;
327        scaleit = 0;
328        let mut n: u64 = 1;
329        let mut eq = 0;
330        'mid: while cmp2_helper(&u, &v, &mut eq) != Equal && eq <= working_prec - 2 {
331            let mut uf;
332            let mut vf;
333            loop {
334                vf = (&u + &v) >> 1;
335                // See proof in algorithms.tex
336                if eq > working_prec >> 2 {
337                    // vf = V(k)
338                    let low_p = (working_prec + 1) >> 1;
339                    let (mut w, o) = v.sub_prec_ref_ref(&u, low_p); // e = V(k-1)-U(k-1)
340                    let mut underflow = test_underflow(&w, o);
341                    let o = w.square_round_assign(Nearest); // e = e^2
342                    underflow |= test_underflow(&w, o);
343                    let o = w.shr_round_assign(4, Nearest); // e*= (1/2)^2*1/4
344                    underflow |= test_underflow(&w, o);
345                    let o = w.div_prec_assign_ref(&vf, low_p); // 1/4*e^2/V(k)
346                    underflow |= test_underflow(&w, o);
347                    let vf_exp = vf.get_exponent().unwrap();
348                    if !underflow {
349                        v = vf.sub_prec(w, working_prec).0;
350                        // 0 or 1
351                        err = u64::exact_from(vf_exp - v.get_exponent().unwrap());
352                        break 'mid;
353                    }
354                    // There has been an underflow because of the cancellation between V(k-1) and
355                    // U(k-1). Let's use the conventional method.
356                }
357                // U(k) increases, so that U.V can overflow (but not underflow).
358                uf = &u * &v;
359                // For multiplication using Nearest, is_infinite is sufficient for overflow checking
360                if uf.is_infinite() {
361                    let scale2 = -(((u.get_exponent().unwrap() + v.get_exponent().unwrap())
362                        - Float::MAX_EXPONENT
363                        + 1)
364                        / 2);
365                    u <<= scale2;
366                    v <<= scale2;
367                    scaleit += scale2;
368                } else {
369                    break;
370                }
371            }
372            u = uf.sqrt();
373            swap(&mut v, &mut vf);
374            n += 1;
375        }
376        // the error on v is bounded by (18n+51) ulps, or twice if there was an exponent loss in the
377        // final subtraction
378        //
379        // 18n+51 should not overflow since n is about log(p)
380        err += (18 * n + 51).ceiling_log_base_2();
381        // we should have n+2 <= 2^(p/4) [see algorithms.tex]
382        if (n + 2).ceiling_log_base_2() <= working_prec >> 2
383            && float_can_round(v.significand_ref().unwrap(), working_prec - err, prec, rm)
384        {
385            break;
386        }
387        working_prec += increment;
388        increment = working_prec >> 1;
389    }
390    v.shr_prec_round(scaleop + scaleit, prec, rm)
391}
392
393fn agm_rational_helper(
394    x: &Rational,
395    y: &Rational,
396    prec: u64,
397    rm: RoundingMode,
398) -> (Float, Ordering) {
399    let mut working_prec = prec + 10;
400    let mut increment = Limb::WIDTH;
401    loop {
402        let (x_lo, x_o) = Float::from_rational_prec_round_ref(x, working_prec, Floor);
403        let (y_lo, y_o) = Float::from_rational_prec_round_ref(y, working_prec, Floor);
404        if x_o == Equal && y_o == Equal {
405            return agm_prec_round_normal(x_lo, y_lo, prec, rm);
406        }
407        let (x_lo, x_hi) = floor_and_ceiling((x_lo, x_o));
408        let (y_lo, y_hi) = floor_and_ceiling((y_lo, y_o));
409        let (agm_lo, mut o_lo) = agm_prec_round_normal(x_lo, y_lo, prec, rm);
410        let (agm_hi, mut o_hi) = agm_prec_round_normal(x_hi, y_hi, prec, rm);
411        if o_lo == Equal {
412            o_lo = o_hi;
413        }
414        if o_hi == Equal {
415            o_hi = o_lo;
416        }
417        if o_lo == o_hi && agm_lo == agm_hi {
418            return (agm_lo, o_lo);
419        }
420        working_prec += increment;
421        increment = working_prec >> 1;
422    }
423}
424
425fn agm_rational_helper_extended(
426    x: &Rational,
427    y: &Rational,
428    prec: u64,
429    rm: RoundingMode,
430) -> (Float, Ordering) {
431    let mut working_prec = prec + 10;
432    let mut increment = Limb::WIDTH;
433    loop {
434        let (x_lo, x_o) = ExtendedFloat::from_rational_prec_round_ref(x, working_prec, Floor);
435        let (y_lo, y_o) = ExtendedFloat::from_rational_prec_round_ref(y, working_prec, Floor);
436        if x_o == Equal && y_o == Equal {
437            let (agm, o) = agm_prec_round_normal_extended(x_lo, y_lo, prec, rm);
438            return agm.into_float_helper(prec, rm, o);
439        }
440        let (x_lo, x_hi) = crate::float::basic::extended::floor_and_ceiling((x_lo, x_o));
441        let (y_lo, y_hi) = crate::float::basic::extended::floor_and_ceiling((y_lo, y_o));
442        let (agm_lo, mut o_lo) = agm_prec_round_normal_extended(x_lo, y_lo, prec, rm);
443        let (agm_hi, mut o_hi) = agm_prec_round_normal_extended(x_hi, y_hi, prec, rm);
444        if o_lo == Equal {
445            o_lo = o_hi;
446        }
447        if o_hi == Equal {
448            o_hi = o_lo;
449        }
450        if o_lo == o_hi && agm_lo == agm_hi {
451            return agm_lo.into_float_helper(prec, rm, o_lo);
452        }
453        working_prec += increment;
454        increment = working_prec >> 1;
455    }
456}
457
458impl Float {
459    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
460    /// specified precision and with the specified rounding mode. Both [`Float`]s are taken by
461    /// value. An [`Ordering`] is also returned, indicating whether the rounded AGM is less than,
462    /// equal to, or greater than the exact AGM. Although `NaN`s are not comparable to any
463    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
464    ///
465    /// See [`RoundingMode`] for a description of the possible rounding modes.
466    ///
467    /// $$
468    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
469    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
470    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
471    /// $$
472    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
473    ///   to be 0.
474    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
475    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
476    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
477    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
478    ///
479    /// If the output has a precision, it is `prec`.
480    ///
481    /// Special cases:
482    /// - $f(\text{NaN},x,p,m)=f(x,\text{NaN},p,m)=f(-\infty,x,p,m)=f(x,-\infty,p,m)=\text{NaN}$
483    /// - $f(\infty,x,p,m)=f(x,\infty,p,m)=\text{NaN}$ if $x\neq\infty$
484    /// - $f(\infty,\infty,p,m)=\infty$
485    /// - $f(\pm0.0,x,p,m)=f(x,\pm0.0,p,m)=0.0$
486    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
487    ///
488    /// Neither overflow nor underflow is possible.
489    ///
490    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec`] instead. If you
491    /// know that your target precision is the maximum of the precisions of the two inputs, consider
492    /// using [`Float::agm_round`] instead. If both of these things are true, consider using
493    /// [`Float::agm`] instead.
494    ///
495    /// # Worst-case complexity
496    /// $T(n) = O(n (\log n)^2 \log\log n)$
497    ///
498    /// $M(n) = O(n \log n)$
499    ///
500    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
501    ///
502    /// # Panics
503    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
504    /// exact result is therefore irrational).
505    ///
506    /// # Examples
507    /// ```
508    /// use malachite_base::rounding_modes::RoundingMode::*;
509    /// use malachite_float::Float;
510    /// use std::cmp::Ordering::*;
511    ///
512    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 5, Floor);
513    /// assert_eq!(agm.to_string(), "13.0");
514    /// assert_eq!(o, Less);
515    ///
516    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 5, Ceiling);
517    /// assert_eq!(agm.to_string(), "13.5");
518    /// assert_eq!(o, Greater);
519    ///
520    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 5, Nearest);
521    /// assert_eq!(agm.to_string(), "13.5");
522    /// assert_eq!(o, Greater);
523    ///
524    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 20, Floor);
525    /// assert_eq!(agm.to_string(), "13.458160");
526    /// assert_eq!(o, Less);
527    ///
528    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 20, Ceiling);
529    /// assert_eq!(agm.to_string(), "13.458176");
530    /// assert_eq!(o, Greater);
531    ///
532    /// let (agm, o) = Float::from(24).agm_prec_round(Float::from(6), 20, Nearest);
533    /// assert_eq!(agm.to_string(), "13.458176");
534    /// assert_eq!(o, Greater);
535    /// ```
536    #[inline]
537    pub fn agm_prec_round(self, other: Self, prec: u64, rm: RoundingMode) -> (Self, Ordering) {
538        assert_ne!(prec, 0);
539        match (&self, &other) {
540            (float_nan!(), _) | (_, float_nan!()) => (float_nan!(), Equal),
541            (float_infinity!(), x) | (x, float_infinity!()) if *x > 0.0 => {
542                (float_infinity!(), Equal)
543            }
544            (float_either_infinity!(), _) | (_, float_either_infinity!()) => (float_nan!(), Equal),
545            (float_either_zero!(), _) | (_, float_either_zero!()) => (float_zero!(), Equal),
546            _ => agm_prec_round_normal(self, other, prec, rm),
547        }
548    }
549
550    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
551    /// specified precision and with the specified rounding mode. The first [`Float`] is taken by
552    /// value and the second by reference. An [`Ordering`] is also returned, indicating whether the
553    /// rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are not
554    /// comparable to any [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
555    ///
556    /// See [`RoundingMode`] for a description of the possible rounding modes.
557    ///
558    /// $$
559    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
560    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
561    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
562    /// $$
563    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
564    ///   to be 0.
565    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
566    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
567    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
568    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
569    ///
570    /// If the output has a precision, it is `prec`.
571    ///
572    /// Special cases:
573    /// - $f(\text{NaN},x,p,m)=f(x,\text{NaN},p,m)=f(-\infty,x,p,m)=f(x,-\infty,p,m)=\text{NaN}$
574    /// - $f(\infty,x,p,m)=f(x,\infty,p,m)=\text{NaN}$ if $x\neq\infty$
575    /// - $f(\infty,\infty,p,m)=\infty$
576    /// - $f(\pm0.0,x,p,m)=f(x,\pm0.0,p,m)=0.0$
577    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
578    ///
579    /// Neither overflow nor underflow is possible.
580    ///
581    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec_val_ref`] instead.
582    /// If you know that your target precision is the maximum of the precisions of the two inputs,
583    /// consider using [`Float::agm_round_val_ref`] instead. If both of these things are true,
584    /// consider using [`Float::agm`] instead.
585    ///
586    /// # Worst-case complexity
587    /// $T(n) = O(n (\log n)^2 \log\log n)$
588    ///
589    /// $M(n) = O(n \log n)$
590    ///
591    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
592    ///
593    /// # Panics
594    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
595    /// exact result is therefore irrational).
596    ///
597    /// # Examples
598    /// ```
599    /// use malachite_base::rounding_modes::RoundingMode::*;
600    /// use malachite_float::Float;
601    /// use std::cmp::Ordering::*;
602    ///
603    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 5, Floor);
604    /// assert_eq!(agm.to_string(), "13.0");
605    /// assert_eq!(o, Less);
606    ///
607    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 5, Ceiling);
608    /// assert_eq!(agm.to_string(), "13.5");
609    /// assert_eq!(o, Greater);
610    ///
611    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 5, Nearest);
612    /// assert_eq!(agm.to_string(), "13.5");
613    /// assert_eq!(o, Greater);
614    ///
615    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 20, Floor);
616    /// assert_eq!(agm.to_string(), "13.458160");
617    /// assert_eq!(o, Less);
618    ///
619    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 20, Ceiling);
620    /// assert_eq!(agm.to_string(), "13.458176");
621    /// assert_eq!(o, Greater);
622    ///
623    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 20, Nearest);
624    /// assert_eq!(agm.to_string(), "13.458176");
625    /// assert_eq!(o, Greater);
626    /// ```
627    #[inline]
628    pub fn agm_prec_round_val_ref(
629        mut self,
630        other: &Self,
631        prec: u64,
632        rm: RoundingMode,
633    ) -> (Self, Ordering) {
634        let o = self.agm_prec_round_assign_ref(other, prec, rm);
635        (self, o)
636    }
637
638    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
639    /// specified precision and with the specified rounding mode. The first [`Float`] is taken by
640    /// reference and the second by value. An [`Ordering`] is also returned, indicating whether the
641    /// rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are not
642    /// comparable to any [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
643    ///
644    /// See [`RoundingMode`] for a description of the possible rounding modes.
645    ///
646    /// $$
647    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
648    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
649    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
650    /// $$
651    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
652    ///   to be 0.
653    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
654    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
655    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
656    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
657    ///
658    /// If the output has a precision, it is `prec`.
659    ///
660    /// Special cases:
661    /// - $f(\text{NaN},x,p,m)=f(x,\text{NaN},p,m)=f(-\infty,x,p,m)=f(x,-\infty,p,m)=\text{NaN}$
662    /// - $f(\infty,x,p,m)=f(x,\infty,p,m)=\text{NaN}$ if $x\neq\infty$
663    /// - $f(\infty,\infty,p,m)=\infty$
664    /// - $f(\pm0.0,x,p,m)=f(x,\pm0.0,p,m)=0.0$
665    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
666    ///
667    /// Neither overflow nor underflow is possible.
668    ///
669    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec_ref_val`] instead.
670    /// If you know that your target precision is the maximum of the precisions of the two inputs,
671    /// consider using [`Float::agm_round_ref_val`] instead. If both of these things are true,
672    /// consider using [`Float::agm`] instead.
673    ///
674    /// # Worst-case complexity
675    /// $T(n) = O(n (\log n)^2 \log\log n)$
676    ///
677    /// $M(n) = O(n \log n)$
678    ///
679    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
680    ///
681    /// # Panics
682    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
683    /// exact result is therefore irrational).
684    ///
685    /// # Examples
686    /// ```
687    /// use malachite_base::rounding_modes::RoundingMode::*;
688    /// use malachite_float::Float;
689    /// use std::cmp::Ordering::*;
690    ///
691    /// let (agm, o) = Float::from(24).agm_prec_round_val_ref(&Float::from(6), 5, Floor);
692    /// assert_eq!(agm.to_string(), "13.0");
693    /// assert_eq!(o, Less);
694    ///
695    /// let (agm, o) = Float::from(24).agm_prec_round_ref_val(Float::from(6), 5, Ceiling);
696    /// assert_eq!(agm.to_string(), "13.5");
697    /// assert_eq!(o, Greater);
698    ///
699    /// let (agm, o) = Float::from(24).agm_prec_round_ref_val(Float::from(6), 5, Nearest);
700    /// assert_eq!(agm.to_string(), "13.5");
701    /// assert_eq!(o, Greater);
702    ///
703    /// let (agm, o) = Float::from(24).agm_prec_round_ref_val(Float::from(6), 20, Floor);
704    /// assert_eq!(agm.to_string(), "13.458160");
705    /// assert_eq!(o, Less);
706    ///
707    /// let (agm, o) = Float::from(24).agm_prec_round_ref_val(Float::from(6), 20, Ceiling);
708    /// assert_eq!(agm.to_string(), "13.458176");
709    /// assert_eq!(o, Greater);
710    ///
711    /// let (agm, o) = Float::from(24).agm_prec_round_ref_val(Float::from(6), 20, Nearest);
712    /// assert_eq!(agm.to_string(), "13.458176");
713    /// assert_eq!(o, Greater);
714    /// ```
715    #[inline]
716    pub fn agm_prec_round_ref_val(
717        &self,
718        mut other: Self,
719        prec: u64,
720        rm: RoundingMode,
721    ) -> (Self, Ordering) {
722        let o = other.agm_prec_round_assign_ref(self, prec, rm);
723        (other, o)
724    }
725
726    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
727    /// specified precision and with the specified rounding mode. Both [`Float`]s are taken by
728    /// reference. An [`Ordering`] is also returned, indicating whether the rounded AGM is less
729    /// than, equal to, or greater than the exact AGM. Although `NaN`s are not comparable to any
730    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
731    ///
732    /// See [`RoundingMode`] for a description of the possible rounding modes.
733    ///
734    /// $$
735    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
736    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
737    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
738    /// $$
739    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
740    ///   to be 0.
741    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
742    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
743    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
744    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
745    ///
746    /// If the output has a precision, it is `prec`.
747    ///
748    /// Special cases:
749    /// - $f(\text{NaN},x,p,m)=f(x,\text{NaN},p,m)=f(-\infty,x,p,m)=f(x,-\infty,p,m)=\text{NaN}$
750    /// - $f(\infty,x,p,m)=f(x,\infty,p,m)=\text{NaN}$ if $x\neq\infty$
751    /// - $f(\infty,\infty,p,m)=\infty$
752    /// - $f(\pm0.0,x,p,m)=f(x,\pm0.0,p,m)=0.0$
753    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
754    ///
755    /// Neither overflow nor underflow is possible.
756    ///
757    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec_ref_ref`] instead.
758    /// If you know that your target precision is the maximum of the precisions of the two inputs,
759    /// consider using [`Float::agm_round_ref_ref`] instead. If both of these things are true,
760    /// consider using [`Float::agm`] instead.
761    ///
762    /// # Worst-case complexity
763    /// $T(n) = O(n (\log n)^2 \log\log n)$
764    ///
765    /// $M(n) = O(n \log n)$
766    ///
767    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
768    ///
769    /// # Panics
770    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
771    /// exact result is therefore irrational).
772    ///
773    /// # Examples
774    /// ```
775    /// use malachite_base::rounding_modes::RoundingMode::*;
776    /// use malachite_float::Float;
777    /// use std::cmp::Ordering::*;
778    ///
779    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 5, Floor);
780    /// assert_eq!(agm.to_string(), "13.0");
781    /// assert_eq!(o, Less);
782    ///
783    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 5, Ceiling);
784    /// assert_eq!(agm.to_string(), "13.5");
785    /// assert_eq!(o, Greater);
786    ///
787    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 5, Nearest);
788    /// assert_eq!(agm.to_string(), "13.5");
789    /// assert_eq!(o, Greater);
790    ///
791    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 20, Floor);
792    /// assert_eq!(agm.to_string(), "13.458160");
793    /// assert_eq!(o, Less);
794    ///
795    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 20, Ceiling);
796    /// assert_eq!(agm.to_string(), "13.458176");
797    /// assert_eq!(o, Greater);
798    ///
799    /// let (agm, o) = Float::from(24).agm_prec_round_ref_ref(&Float::from(6), 20, Nearest);
800    /// assert_eq!(agm.to_string(), "13.458176");
801    /// assert_eq!(o, Greater);
802    /// ```
803    ///
804    /// This is mpfr_agm from agm.c, MPFR 4.3.0.
805    #[inline]
806    pub fn agm_prec_round_ref_ref(
807        &self,
808        other: &Self,
809        prec: u64,
810        rm: RoundingMode,
811    ) -> (Self, Ordering) {
812        assert_ne!(prec, 0);
813        match (self, other) {
814            (float_nan!(), _) | (_, float_nan!()) => (float_nan!(), Equal),
815            (float_infinity!(), x) | (x, float_infinity!()) if *x > 0.0 => {
816                (float_infinity!(), Equal)
817            }
818            (float_either_infinity!(), _) | (_, float_either_infinity!()) => (float_nan!(), Equal),
819            (float_either_zero!(), _) | (_, float_either_zero!()) => (float_zero!(), Equal),
820            _ => agm_prec_round_ref_ref_normal(self, other, prec, rm),
821        }
822    }
823
824    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
825    /// nearest value of the specified precision. Both [`Float`]s are taken by value. An
826    /// [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to, or
827    /// greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
828    /// this function returns a `NaN` it also returns `Equal`.
829    ///
830    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
831    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
832    /// the `Nearest` rounding mode.
833    ///
834    /// $$
835    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
836    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
837    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
838    /// $$
839    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
840    ///   to be 0.
841    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
842    ///   \text{AGM}(x,y)\rfloor-p}$.
843    ///
844    /// If the output has a precision, it is `prec`.
845    ///
846    /// Special cases:
847    /// - $f(\text{NaN},x,p)=f(x,\text{NaN},p)=f(-\infty,x,p)=f(x,-\infty,p)=\text{NaN}$
848    /// - $f(\infty,x,p)=f(x,\infty,p)=\text{NaN}$ if $x\neq\infty$
849    /// - $f(\infty,\infty,p)=\infty$
850    /// - $f(\pm0.0,x,p)=f(x,\pm0.0,p)=0.0$
851    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
852    ///
853    /// Neither overflow nor underflow is possible.
854    ///
855    /// If you want to use a rounding mode other than `Nearest`, consider using
856    /// [`Float::agm_prec_round`] instead. If you know that your target precision is the maximum of
857    /// the precisions of the two inputs, consider using [`Float::agm`] instead.
858    ///
859    /// # Worst-case complexity
860    /// $T(n) = O(n (\log n)^2 \log\log n)$
861    ///
862    /// $M(n) = O(n \log n)$
863    ///
864    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
865    ///
866    /// # Examples
867    /// ```
868    /// use malachite_float::Float;
869    /// use std::cmp::Ordering::*;
870    ///
871    /// let (agm, o) = Float::from(24).agm_prec(Float::from(6), 5);
872    /// assert_eq!(agm.to_string(), "13.5");
873    /// assert_eq!(o, Greater);
874    ///
875    /// let (agm, o) = Float::from(24).agm_prec(Float::from(6), 20);
876    /// assert_eq!(agm.to_string(), "13.458176");
877    /// assert_eq!(o, Greater);
878    /// ```
879    #[inline]
880    pub fn agm_prec(self, other: Self, prec: u64) -> (Self, Ordering) {
881        self.agm_prec_round(other, prec, Nearest)
882    }
883
884    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
885    /// nearest value of the specified precision. The first [`Float`] is taken by value and the
886    /// second by reference. An [`Ordering`] is also returned, indicating whether the rounded AGM is
887    /// less than, equal to, or greater than the exact AGM. Although `NaN`s are not comparable to
888    /// any [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
889    ///
890    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
891    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
892    /// the `Nearest` rounding mode.
893    ///
894    /// $$
895    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
896    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
897    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
898    /// $$
899    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
900    ///   to be 0.
901    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
902    ///   \text{AGM}(x,y)\rfloor-p}$.
903    ///
904    /// If the output has a precision, it is `prec`.
905    ///
906    /// Special cases:
907    /// - $f(\text{NaN},x,p)=f(x,\text{NaN},p)=f(-\infty,x,p)=f(x,-\infty,p)=\text{NaN}$
908    /// - $f(\infty,x,p)=f(x,\infty,p)=\text{NaN}$ if $x\neq\infty$
909    /// - $f(\infty,\infty,p)=\infty$
910    /// - $f(\pm0.0,x,p)=f(x,\pm0.0,p)=0.0$
911    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
912    ///
913    /// Neither overflow nor underflow is possible.
914    ///
915    /// If you want to use a rounding mode other than `Nearest`, consider using
916    /// [`Float::agm_prec_round_val_ref`] instead. If you know that your target precision is the
917    /// maximum of the precisions of the two inputs, consider using [`Float::agm`] instead.
918    ///
919    /// # Worst-case complexity
920    /// $T(n) = O(n (\log n)^2 \log\log n)$
921    ///
922    /// $M(n) = O(n \log n)$
923    ///
924    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
925    ///
926    /// # Examples
927    /// ```
928    /// use malachite_float::Float;
929    /// use std::cmp::Ordering::*;
930    ///
931    /// let (agm, o) = Float::from(24).agm_prec_val_ref(&Float::from(6), 5);
932    /// assert_eq!(agm.to_string(), "13.5");
933    /// assert_eq!(o, Greater);
934    ///
935    /// let (agm, o) = Float::from(24).agm_prec_val_ref(&Float::from(6), 20);
936    /// assert_eq!(agm.to_string(), "13.458176");
937    /// assert_eq!(o, Greater);
938    /// ```
939    #[inline]
940    pub fn agm_prec_val_ref(self, other: &Self, prec: u64) -> (Self, Ordering) {
941        self.agm_prec_round_val_ref(other, prec, Nearest)
942    }
943
944    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
945    /// nearest value of the specified precision. The first [`Float`] is taken by reference and the
946    /// second by value. An [`Ordering`] is also returned, indicating whether the rounded AGM is
947    /// less than, equal to, or greater than the exact AGM. Although `NaN`s are not comparable to
948    /// any [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
949    ///
950    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
951    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
952    /// the `Nearest` rounding mode.
953    ///
954    /// $$
955    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
956    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
957    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
958    /// $$
959    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
960    ///   to be 0.
961    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
962    ///   \text{AGM}(x,y)\rfloor-p}$.
963    ///
964    /// If the output has a precision, it is `prec`.
965    ///
966    /// Special cases:
967    /// - $f(\text{NaN},x,p)=f(x,\text{NaN},p)=f(-\infty,x,p)=f(x,-\infty,p)=\text{NaN}$
968    /// - $f(\infty,x,p)=f(x,\infty,p)=\text{NaN}$ if $x\neq\infty$
969    /// - $f(\infty,\infty,p)=\infty$
970    /// - $f(\pm0.0,x,p)=f(x,\pm0.0,p)=0.0$
971    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
972    ///
973    /// Neither overflow nor underflow is possible.
974    ///
975    /// If you want to use a rounding mode other than `Nearest`, consider using
976    /// [`Float::agm_prec_round_ref_val`] instead. If you know that your target precision is the
977    /// maximum of the precisions of the two inputs, consider using [`Float::agm`] instead.
978    ///
979    /// # Worst-case complexity
980    /// $T(n) = O(n (\log n)^2 \log\log n)$
981    ///
982    /// $M(n) = O(n \log n)$
983    ///
984    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
985    ///
986    /// # Examples
987    /// ```
988    /// use malachite_float::Float;
989    /// use std::cmp::Ordering::*;
990    ///
991    /// let (agm, o) = (&Float::from(24)).agm_prec_ref_val(Float::from(6), 5);
992    /// assert_eq!(agm.to_string(), "13.5");
993    /// assert_eq!(o, Greater);
994    ///
995    /// let (agm, o) = (&Float::from(24)).agm_prec_ref_val(Float::from(6), 20);
996    /// assert_eq!(agm.to_string(), "13.458176");
997    /// assert_eq!(o, Greater);
998    /// ```
999    #[inline]
1000    pub fn agm_prec_ref_val(&self, other: Self, prec: u64) -> (Self, Ordering) {
1001        self.agm_prec_round_ref_val(other, prec, Nearest)
1002    }
1003
1004    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result to the
1005    /// nearest value of the specified precision. Both [`Float`]s are taken by reference. An
1006    /// [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to, or
1007    /// greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
1008    /// this function returns a `NaN` it also returns `Equal`.
1009    ///
1010    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
1011    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
1012    /// the `Nearest` rounding mode.
1013    ///
1014    /// $$
1015    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
1016    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1017    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1018    /// $$
1019    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1020    ///   to be 0.
1021    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
1022    ///   \text{AGM}(x,y)\rfloor-p}$.
1023    ///
1024    /// If the output has a precision, it is `prec`.
1025    ///
1026    /// Special cases:
1027    /// - $f(\text{NaN},x,p)=f(x,\text{NaN},p)=f(-\infty,x,p)=f(x,-\infty,p)=\text{NaN}$
1028    /// - $f(\infty,x,p)=f(x,\infty,p)=\text{NaN}$ if $x\neq\infty$
1029    /// - $f(\infty,\infty,p)=\infty$
1030    /// - $f(\pm0.0,x,p)=f(x,\pm0.0,p)=0.0$
1031    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
1032    ///
1033    /// Neither overflow nor underflow is possible.
1034    ///
1035    /// If you want to use a rounding mode other than `Nearest`, consider using
1036    /// [`Float::agm_prec_round_ref_ref`] instead. If you know that your target precision is the
1037    /// maximum of the precisions of the two inputs, consider using [`Float::agm`] instead.
1038    ///
1039    /// # Worst-case complexity
1040    /// $T(n) = O(n (\log n)^2 \log\log n)$
1041    ///
1042    /// $M(n) = O(n \log n)$
1043    ///
1044    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1045    ///
1046    /// # Examples
1047    /// ```
1048    /// use malachite_float::Float;
1049    /// use std::cmp::Ordering::*;
1050    ///
1051    /// let (agm, o) = (&Float::from(24)).agm_prec_ref_ref(&Float::from(6), 5);
1052    /// assert_eq!(agm.to_string(), "13.5");
1053    /// assert_eq!(o, Greater);
1054    ///
1055    /// let (agm, o) = (&Float::from(24)).agm_prec_ref_ref(&Float::from(6), 20);
1056    /// assert_eq!(agm.to_string(), "13.458176");
1057    /// assert_eq!(o, Greater);
1058    /// ```
1059    #[inline]
1060    pub fn agm_prec_ref_ref(&self, other: &Self, prec: u64) -> (Self, Ordering) {
1061        self.agm_prec_round_ref_ref(other, prec, Nearest)
1062    }
1063
1064    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result with the
1065    /// specified rounding mode. Both [`Float`]s are taken by value. An [`Ordering`] is also
1066    /// returned, indicating whether the rounded AGM is less than, equal to, or greater than the
1067    /// exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever this function
1068    /// returns a `NaN` it also returns `Equal`.
1069    ///
1070    /// The precision of the output is the maximum of the precision of the inputs. See
1071    /// [`RoundingMode`] for a description of the possible rounding modes.
1072    ///
1073    /// $$
1074    /// f(x,y,m) = \text{AGM}(x,y)+\varepsilon
1075    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1076    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1077    /// $$
1078    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1079    ///   to be 0.
1080    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1081    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1082    ///   inputs.
1083    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1084    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1085    ///   inputs.
1086    ///
1087    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1088    ///
1089    /// Special cases:
1090    /// - $f(\text{NaN},x,m)=f(x,\text{NaN},m)=f(-\infty,x,m)=f(x,-\infty,m)=\text{NaN}$
1091    /// - $f(\infty,x,m)=f(x,\infty,m)=\text{NaN}$ if $x\neq\infty$
1092    /// - $f(\infty,\infty,m)=\infty$
1093    /// - $f(\pm0.0,x,m)=f(x,\pm0.0,m)=0.0$
1094    /// - $f(x,y,m)=\text{NaN}$ if $x<0$ or $y<0$
1095    ///
1096    /// Neither overflow nor underflow is possible.
1097    ///
1098    /// If you want to specify an output precision, consider using [`Float::agm_prec_round`]
1099    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1100    /// [`Float::agm`] instead.
1101    ///
1102    /// # Worst-case complexity
1103    /// $T(n) = O(n (\log n)^2 \log\log n)$
1104    ///
1105    /// $M(n) = O(n \log n)$
1106    ///
1107    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
1108    /// other.significant_bits())`.
1109    ///
1110    /// # Panics
1111    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1112    /// exact result is therefore irrational).
1113    ///
1114    /// # Examples
1115    /// ```
1116    /// use malachite_base::rounding_modes::RoundingMode::*;
1117    /// use malachite_float::Float;
1118    /// use std::cmp::Ordering::*;
1119    ///
1120    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1121    ///     .0
1122    ///     .agm_round(Float::from(6), Floor);
1123    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156964");
1124    /// assert_eq!(o, Less);
1125    ///
1126    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1127    ///     .0
1128    ///     .agm_round(Float::from(6), Ceiling);
1129    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1130    /// assert_eq!(o, Greater);
1131    ///
1132    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1133    ///     .0
1134    ///     .agm_round(Float::from(6), Nearest);
1135    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1136    /// assert_eq!(o, Greater);
1137    /// ```
1138    #[inline]
1139    pub fn agm_round(self, other: Self, rm: RoundingMode) -> (Self, Ordering) {
1140        let prec = max(self.significant_bits(), other.significant_bits());
1141        self.agm_prec_round(other, prec, rm)
1142    }
1143
1144    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result with the
1145    /// specified rounding mode. The first [`Float`] is taken by value and the second by reference.
1146    /// An [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to,
1147    /// or greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
1148    /// this function returns a `NaN` it also returns `Equal`.
1149    ///
1150    /// The precision of the output is the maximum of the precision of the inputs. See
1151    /// [`RoundingMode`] for a description of the possible rounding modes.
1152    ///
1153    /// $$
1154    /// f(x,y,m) = \text{AGM}(x,y)+\varepsilon
1155    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1156    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1157    /// $$
1158    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1159    ///   to be 0.
1160    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1161    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1162    ///   inputs.
1163    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1164    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1165    ///   inputs.
1166    ///
1167    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1168    ///
1169    /// Special cases:
1170    /// - $f(\text{NaN},x,m)=f(x,\text{NaN},m)=f(-\infty,x,m)=f(x,-\infty,m)=\text{NaN}$
1171    /// - $f(\infty,x,m)=f(x,\infty,m)=\text{NaN}$ if $x\neq\infty$
1172    /// - $f(\infty,\infty,m)=\infty$
1173    /// - $f(\pm0.0,x,m)=f(x,\pm0.0,m)=0.0$
1174    /// - $f(x,y,m)=\text{NaN}$ if $x<0$ or $y<0$
1175    ///
1176    /// Neither overflow nor underflow is possible.
1177    ///
1178    /// If you want to specify an output precision, consider using [`Float::agm_prec_round_val_ref`]
1179    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1180    /// [`Float::agm`] instead.
1181    ///
1182    /// # Worst-case complexity
1183    /// $T(n) = O(n (\log n)^2 \log\log n)$
1184    ///
1185    /// $M(n) = O(m)$
1186    ///
1187    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
1188    /// other.significant_bits())`, and $m$ is `other.significant_bits()`.
1189    ///
1190    /// # Panics
1191    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1192    /// exact result is therefore irrational).
1193    ///
1194    /// # Examples
1195    /// ```
1196    /// use malachite_base::rounding_modes::RoundingMode::*;
1197    /// use malachite_float::Float;
1198    /// use std::cmp::Ordering::*;
1199    ///
1200    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1201    ///     .0
1202    ///     .agm_round_val_ref(&Float::from(6), Floor);
1203    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156964");
1204    /// assert_eq!(o, Less);
1205    ///
1206    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1207    ///     .0
1208    ///     .agm_round_val_ref(&Float::from(6), Ceiling);
1209    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1210    /// assert_eq!(o, Greater);
1211    ///
1212    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1213    ///     .0
1214    ///     .agm_round_val_ref(&Float::from(6), Nearest);
1215    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1216    /// assert_eq!(o, Greater);
1217    /// ```
1218    #[inline]
1219    pub fn agm_round_val_ref(self, other: &Self, rm: RoundingMode) -> (Self, Ordering) {
1220        let prec = max(self.significant_bits(), other.significant_bits());
1221        self.agm_prec_round_val_ref(other, prec, rm)
1222    }
1223
1224    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result with the
1225    /// specified rounding mode. The first [`Float`] is taken by reference and the second by value.
1226    /// An [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to,
1227    /// or greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
1228    /// this function returns a `NaN` it also returns `Equal`.
1229    ///
1230    /// The precision of the output is the maximum of the precision of the inputs. See
1231    /// [`RoundingMode`] for a description of the possible rounding modes.
1232    ///
1233    /// $$
1234    /// f(x,y,m) = \text{AGM}(x,y)+\varepsilon
1235    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1236    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1237    /// $$
1238    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1239    ///   to be 0.
1240    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1241    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1242    ///   inputs.
1243    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1244    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1245    ///   inputs.
1246    ///
1247    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1248    ///
1249    /// Special cases:
1250    /// - $f(\text{NaN},x,m)=f(x,\text{NaN},m)=f(-\infty,x,m)=f(x,-\infty,m)=\text{NaN}$
1251    /// - $f(\infty,x,m)=f(x,\infty,m)=\text{NaN}$ if $x\neq\infty$
1252    /// - $f(\infty,\infty,m)=\infty$
1253    /// - $f(\pm0.0,x,m)=f(x,\pm0.0,m)=0.0$
1254    /// - $f(x,y,m)=\text{NaN}$ if $x<0$ or $y<0$
1255    ///
1256    /// Neither overflow nor underflow is possible.
1257    ///
1258    /// If you want to specify an output precision, consider using [`Float::agm_prec_round_ref_val`]
1259    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1260    /// [`Float::agm`] instead.
1261    ///
1262    /// # Worst-case complexity
1263    /// $T(n) = O(n (\log n)^2 \log\log n)$
1264    ///
1265    /// $M(n) = O(m)$
1266    ///
1267    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
1268    /// other.significant_bits())`, and $m$ is `self.significant_bits()`.
1269    ///
1270    /// # Panics
1271    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1272    /// exact result is therefore irrational).
1273    ///
1274    /// # Examples
1275    /// ```
1276    /// use malachite_base::rounding_modes::RoundingMode::*;
1277    /// use malachite_float::Float;
1278    /// use std::cmp::Ordering::*;
1279    ///
1280    /// let (agm, o) =
1281    ///     (&Float::from_unsigned_prec(24u8, 100).0).agm_round_ref_val(Float::from(6), Floor);
1282    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156964");
1283    /// assert_eq!(o, Less);
1284    ///
1285    /// let (agm, o) =
1286    ///     (&Float::from_unsigned_prec(24u8, 100).0).agm_round_ref_val(Float::from(6), Ceiling);
1287    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1288    /// assert_eq!(o, Greater);
1289    ///
1290    /// let (agm, o) =
1291    ///     (&Float::from_unsigned_prec(24u8, 100).0).agm_round_ref_val(Float::from(6), Nearest);
1292    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1293    /// assert_eq!(o, Greater);
1294    /// ```
1295    #[inline]
1296    pub fn agm_round_ref_val(&self, other: Self, rm: RoundingMode) -> (Self, Ordering) {
1297        let prec = max(self.significant_bits(), other.significant_bits());
1298        self.agm_prec_round_ref_val(other, prec, rm)
1299    }
1300
1301    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, rounding the result with the
1302    /// specified rounding mode. Both [`Float`]s are taken by reference. An [`Ordering`] is also
1303    /// returned, indicating whether the rounded AGM is less than, equal to, or greater than the
1304    /// exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever this function
1305    /// returns a `NaN` it also returns `Equal`.
1306    ///
1307    /// The precision of the output is the maximum of the precision of the inputs. See
1308    /// [`RoundingMode`] for a description of the possible rounding modes.
1309    ///
1310    /// $$
1311    /// f(x,y,m) = \text{AGM}(x,y)+\varepsilon
1312    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1313    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1314    /// $$
1315    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1316    ///   to be 0.
1317    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1318    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1319    ///   inputs.
1320    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1321    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1322    ///   inputs.
1323    ///
1324    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1325    ///
1326    /// Special cases:
1327    /// - $f(\text{NaN},x,m)=f(x,\text{NaN},m)=f(-\infty,x,m)=f(x,-\infty,m)=\text{NaN}$
1328    /// - $f(\infty,x,m)=f(x,\infty,m)=\text{NaN}$ if $x\neq\infty$
1329    /// - $f(\infty,\infty,m)=\infty$
1330    /// - $f(\pm0.0,x,m)=f(x,\pm0.0,m)=0.0$
1331    /// - $f(x,y,m)=\text{NaN}$ if $x<0$ or $y<0$
1332    ///
1333    /// Neither overflow nor underflow is possible.
1334    ///
1335    /// If you want to specify an output precision, consider using [`Float::agm_prec_round_ref_ref`]
1336    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1337    /// [`Float::agm`] instead.
1338    ///
1339    /// # Worst-case complexity
1340    /// $T(n) = O(n (\log n)^2 \log\log n)$
1341    ///
1342    /// $M(n) = O(n \log n)$
1343    ///
1344    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
1345    /// other.significant_bits())`.
1346    ///
1347    /// # Panics
1348    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1349    /// exact result is therefore irrational).
1350    ///
1351    /// # Examples
1352    /// ```
1353    /// use malachite_base::rounding_modes::RoundingMode::*;
1354    /// use malachite_float::Float;
1355    /// use std::cmp::Ordering::*;
1356    ///
1357    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1358    ///     .0
1359    ///     .agm_round_ref_ref(&Float::from(6), Floor);
1360    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156964");
1361    /// assert_eq!(o, Less);
1362    ///
1363    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1364    ///     .0
1365    ///     .agm_round_ref_ref(&Float::from(6), Ceiling);
1366    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1367    /// assert_eq!(o, Greater);
1368    ///
1369    /// let (agm, o) = Float::from_unsigned_prec(24u8, 100)
1370    ///     .0
1371    ///     .agm_round_ref_ref(&Float::from(6), Nearest);
1372    /// assert_eq!(agm.to_string(), "13.458171481725615420766813156976");
1373    /// assert_eq!(o, Greater);
1374    /// ```
1375    #[inline]
1376    pub fn agm_round_ref_ref(&self, other: &Self, rm: RoundingMode) -> (Self, Ordering) {
1377        let prec = max(self.significant_bits(), other.significant_bits());
1378        self.agm_prec_round_ref_ref(other, prec, rm)
1379    }
1380
1381    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1382    /// place, and rounding the result to the specified precision and with the specified rounding
1383    /// mode. The [`Float`] on the right-hand side is taken by value. An [`Ordering`] is returned,
1384    /// indicating whether the rounded AGM is less than, equal to, or greater than the exact AGM.
1385    /// Although `NaN`s are not comparable to any [`Float`], whenever this function sets the
1386    /// [`Float`] to `NaN` it also returns `Equal`.
1387    ///
1388    /// See [`RoundingMode`] for a description of the possible rounding modes.
1389    ///
1390    /// $$
1391    /// x \gets \text{AGM}(x,y)+\varepsilon
1392    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1393    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1394    /// $$
1395    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1396    ///   to be 0.
1397    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1398    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
1399    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1400    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
1401    ///
1402    /// If the output has a precision, it is `prec`.
1403    ///
1404    /// See the [`Float::agm_prec_round`] documentation for information on special cases, overflow,
1405    /// and underflow.
1406    ///
1407    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec_assign`] instead. If
1408    /// you know that your target precision is the maximum of the precisions of the two inputs,
1409    /// consider using [`Float::agm_round_assign`] instead. If both of these things are true,
1410    /// consider using [`Float::agm_assign`] instead.
1411    ///
1412    /// # Worst-case complexity
1413    /// $T(n) = O(n (\log n)^2 \log\log n)$
1414    ///
1415    /// $M(n) = O(n \log n)$
1416    ///
1417    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1418    ///
1419    /// # Panics
1420    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1421    /// exact result is therefore irrational).
1422    ///
1423    /// # Examples
1424    /// ```
1425    /// use malachite_base::rounding_modes::RoundingMode::*;
1426    /// use malachite_float::Float;
1427    /// use std::cmp::Ordering::*;
1428    ///
1429    /// let mut x = Float::from(24);
1430    /// assert_eq!(x.agm_prec_round_assign(Float::from(6), 5, Floor), Less);
1431    /// assert_eq!(x.to_string(), "13.0");
1432    ///
1433    /// let mut x = Float::from(24);
1434    /// assert_eq!(x.agm_prec_round_assign(Float::from(6), 5, Ceiling), Greater);
1435    /// assert_eq!(x.to_string(), "13.5");
1436    ///
1437    /// let mut x = Float::from(24);
1438    /// assert_eq!(x.agm_prec_round_assign(Float::from(6), 5, Nearest), Greater);
1439    /// assert_eq!(x.to_string(), "13.5");
1440    ///
1441    /// let mut x = Float::from(24);
1442    /// assert_eq!(x.agm_prec_round_assign(Float::from(6), 20, Floor), Less);
1443    /// assert_eq!(x.to_string(), "13.458160");
1444    ///
1445    /// let mut x = Float::from(24);
1446    /// assert_eq!(
1447    ///     x.agm_prec_round_assign(Float::from(6), 20, Ceiling),
1448    ///     Greater
1449    /// );
1450    /// assert_eq!(x.to_string(), "13.458176");
1451    ///
1452    /// let mut x = Float::from(24);
1453    /// assert_eq!(
1454    ///     x.agm_prec_round_assign(Float::from(6), 20, Nearest),
1455    ///     Greater
1456    /// );
1457    /// assert_eq!(x.to_string(), "13.458176");
1458    /// ```
1459    #[inline]
1460    pub fn agm_prec_round_assign(&mut self, other: Self, prec: u64, rm: RoundingMode) -> Ordering {
1461        let o;
1462        let mut x = Self::ZERO;
1463        swap(&mut x, self);
1464        (*self, o) = x.agm_prec_round(other, prec, rm);
1465        o
1466    }
1467
1468    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1469    /// place, and rounding the result to the specified precision and with the specified rounding
1470    /// mode. The [`Float`] on the right-hand side is taken by reference. An [`Ordering`] is
1471    /// returned, indicating whether the rounded AGM is less than, equal to, or greater than the
1472    /// exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever this function sets
1473    /// the [`Float`] to `NaN` it also returns `Equal`.
1474    ///
1475    /// See [`RoundingMode`] for a description of the possible rounding modes.
1476    ///
1477    /// $$
1478    /// x \gets \text{AGM}(x,y)+\varepsilon
1479    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1480    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1481    /// $$
1482    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1483    ///   to be 0.
1484    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1485    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
1486    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1487    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
1488    ///
1489    /// If the output has a precision, it is `prec`.
1490    ///
1491    /// See the [`Float::agm_prec_round`] documentation for information on special cases, overflow,
1492    /// and underflow.
1493    ///
1494    /// If you know you'll be using `Nearest`, consider using [`Float::agm_prec_assign_ref`]
1495    /// instead. If you know that your target precision is the maximum of the precisions of the two
1496    /// inputs, consider using [`Float::agm_round_assign_ref`] instead. If both of these things are
1497    /// true, consider using [`Float::agm_assign`] instead.
1498    ///
1499    /// # Worst-case complexity
1500    /// $T(n) = O(n (\log n)^2 \log\log n)$
1501    ///
1502    /// $M(n) = O(n \log n)$
1503    ///
1504    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1505    ///
1506    /// # Panics
1507    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1508    /// exact result is therefore irrational).
1509    ///
1510    /// # Examples
1511    /// ```
1512    /// use malachite_base::rounding_modes::RoundingMode::*;
1513    /// use malachite_float::Float;
1514    /// use std::cmp::Ordering::*;
1515    ///
1516    /// let mut x = Float::from(24);
1517    /// assert_eq!(x.agm_prec_round_assign_ref(&Float::from(6), 5, Floor), Less);
1518    /// assert_eq!(x.to_string(), "13.0");
1519    ///
1520    /// let mut x = Float::from(24);
1521    /// assert_eq!(
1522    ///     x.agm_prec_round_assign_ref(&Float::from(6), 5, Ceiling),
1523    ///     Greater
1524    /// );
1525    /// assert_eq!(x.to_string(), "13.5");
1526    ///
1527    /// let mut x = Float::from(24);
1528    /// assert_eq!(
1529    ///     x.agm_prec_round_assign_ref(&Float::from(6), 5, Nearest),
1530    ///     Greater
1531    /// );
1532    /// assert_eq!(x.to_string(), "13.5");
1533    ///
1534    /// let mut x = Float::from(24);
1535    /// assert_eq!(
1536    ///     x.agm_prec_round_assign_ref(&Float::from(6), 20, Floor),
1537    ///     Less
1538    /// );
1539    /// assert_eq!(x.to_string(), "13.458160");
1540    ///
1541    /// let mut x = Float::from(24);
1542    /// assert_eq!(
1543    ///     x.agm_prec_round_assign_ref(&Float::from(6), 20, Ceiling),
1544    ///     Greater
1545    /// );
1546    /// assert_eq!(x.to_string(), "13.458176");
1547    ///
1548    /// let mut x = Float::from(24);
1549    /// assert_eq!(
1550    ///     x.agm_prec_round_assign_ref(&Float::from(6), 20, Nearest),
1551    ///     Greater
1552    /// );
1553    /// assert_eq!(x.to_string(), "13.458176");
1554    /// ```
1555    #[inline]
1556    pub fn agm_prec_round_assign_ref(
1557        &mut self,
1558        other: &Self,
1559        prec: u64,
1560        rm: RoundingMode,
1561    ) -> Ordering {
1562        let o;
1563        (*self, o) = self.agm_prec_round_ref_ref(other, prec, rm);
1564        o
1565    }
1566
1567    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1568    /// place, and rounding the result to the nearest value of the specified precision. The
1569    /// [`Float`] on the right-hand side is taken by value. An [`Ordering`] is returned, indicating
1570    /// whether the rounded AGM is less than, equal to, or greater than the exact AGM. Although
1571    /// `NaN`s are not comparable to any [`Float`], whenever this function sets the [`Float`] to
1572    /// `NaN` it also returns `Equal`.
1573    ///
1574    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
1575    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
1576    /// the `Nearest` rounding mode.
1577    ///
1578    /// $$
1579    /// x \gets \text{AGM}(x,y)+\varepsilon
1580    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1581    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1582    /// $$
1583    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1584    ///   to be 0.
1585    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
1586    ///   \text{AGM}(x,y)\rfloor-p}$.
1587    ///
1588    /// If the output has a precision, it is `prec`.
1589    ///
1590    /// See the [`Float::agm_prec`] documentation for information on special cases, overflow, and
1591    /// underflow.
1592    ///
1593    /// If you want to use a rounding mode other than `Nearest`, consider using
1594    /// [`Float::agm_prec_round_assign`] instead. If you know that your target precision is the
1595    /// maximum of the precisions of the two inputs, consider using [`Float::agm_assign`] instead.
1596    ///
1597    /// # Worst-case complexity
1598    /// $T(n) = O(n (\log n)^2 \log\log n)$
1599    ///
1600    /// $M(n) = O(n \log n)$
1601    ///
1602    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1603    ///
1604    /// # Examples
1605    /// ```
1606    /// use malachite_float::Float;
1607    /// use std::cmp::Ordering::*;
1608    ///
1609    /// let mut x = Float::from(24);
1610    /// assert_eq!(x.agm_prec_assign(Float::from(6), 5), Greater);
1611    /// assert_eq!(x.to_string(), "13.5");
1612    ///
1613    /// let mut x = Float::from(24);
1614    /// assert_eq!(x.agm_prec_assign(Float::from(6), 20), Greater);
1615    /// assert_eq!(x.to_string(), "13.458176");
1616    /// ```
1617    #[inline]
1618    pub fn agm_prec_assign(&mut self, other: Self, prec: u64) -> Ordering {
1619        self.agm_prec_round_assign(other, prec, Nearest)
1620    }
1621
1622    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1623    /// place, and rounding the result to the nearest value of the specified precision. The
1624    /// [`Float`] on the right-hand side is taken by reference. An [`Ordering`] is returned,
1625    /// indicating whether the rounded AGM is less than, equal to, or greater than the exact AGM.
1626    /// Although `NaN`s are not comparable to any [`Float`], whenever this function sets the
1627    /// [`Float`] to `NaN` it also returns `Equal`.
1628    ///
1629    /// If the agm is equidistant from two [`Float`]s with the specified precision, the [`Float`]
1630    /// with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a description of
1631    /// the `Nearest` rounding mode.
1632    ///
1633    /// $$
1634    /// x \gets \text{AGM}(x,y)+\varepsilon
1635    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1636    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1637    /// $$
1638    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1639    ///   to be 0.
1640    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
1641    ///   \text{AGM}(x,y)\rfloor-p}$.
1642    ///
1643    /// If the output has a precision, it is `prec`.
1644    ///
1645    /// See the [`Float::agm_prec`] documentation for information on special cases, overflow, and
1646    /// underflow.
1647    ///
1648    /// If you want to use a rounding mode other than `Nearest`, consider using
1649    /// [`Float::agm_prec_round_assign_ref`] instead. If you know that your target precision is the
1650    /// maximum of the precisions of the two inputs, consider using [`Float::agm_assign`] instead.
1651    ///
1652    /// # Worst-case complexity
1653    /// $T(n) = O(n (\log n)^2 \log\log n)$
1654    ///
1655    /// $M(n) = O(n \log n)$
1656    ///
1657    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1658    ///
1659    /// # Examples
1660    /// ```
1661    /// use malachite_float::Float;
1662    /// use std::cmp::Ordering::*;
1663    ///
1664    /// let mut x = Float::from(24);
1665    /// assert_eq!(x.agm_prec_assign_ref(&Float::from(6), 5), Greater);
1666    /// assert_eq!(x.to_string(), "13.5");
1667    ///
1668    /// let mut x = Float::from(24);
1669    /// assert_eq!(x.agm_prec_assign_ref(&Float::from(6), 20), Greater);
1670    /// assert_eq!(x.to_string(), "13.458176");
1671    /// ```
1672    #[inline]
1673    pub fn agm_prec_assign_ref(&mut self, other: &Self, prec: u64) -> Ordering {
1674        self.agm_prec_round_assign_ref(other, prec, Nearest)
1675    }
1676
1677    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1678    /// place, and rounding the result with the specified rounding mode. The [`Float`] on the
1679    /// right-hand side is taken by value. An [`Ordering`] is returned, indicating whether the
1680    /// rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are not
1681    /// comparable to any [`Float`], whenever this function sets the [`Float`] to `NaN` it also
1682    /// returns `Equal`.
1683    ///
1684    /// The precision of the output is the maximum of the precision of the inputs. See
1685    /// [`RoundingMode`] for a description of the possible rounding modes.
1686    ///
1687    /// $$
1688    /// x \gets \text{AGM}(x,y)+\varepsilon
1689    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1690    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1691    /// $$
1692    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1693    ///   to be 0.
1694    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1695    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1696    ///   inputs.
1697    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1698    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1699    ///   inputs.
1700    ///
1701    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1702    ///
1703    /// See the [`Float::agm_round`] documentation for information on special cases, overflow, and
1704    /// underflow.
1705    ///
1706    /// If you want to specify an output precision, consider using [`Float::agm_prec_round_assign`]
1707    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1708    /// [`Float::agm_assign`] instead.
1709    ///
1710    /// # Worst-case complexity
1711    /// $T(n) = O(n (\log n)^2 \log\log n)$
1712    ///
1713    /// $M(n) = O(n \log n)$
1714    ///
1715    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
1716    /// other.significant_bits())`.
1717    ///
1718    /// # Panics
1719    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1720    /// exact result is therefore irrational).
1721    ///
1722    /// # Examples
1723    /// ```
1724    /// use malachite_base::rounding_modes::RoundingMode::*;
1725    /// use malachite_float::Float;
1726    /// use std::cmp::Ordering::*;
1727    ///
1728    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1729    /// assert_eq!(x.agm_round_assign(Float::from(6), Floor), Less);
1730    /// assert_eq!(x.to_string(), "13.458171481725615420766813156964");
1731    ///
1732    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1733    /// assert_eq!(x.agm_round_assign(Float::from(6), Ceiling), Greater);
1734    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
1735    ///
1736    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1737    /// assert_eq!(x.agm_round_assign(Float::from(6), Nearest), Greater);
1738    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
1739    /// ```
1740    #[inline]
1741    pub fn agm_round_assign(&mut self, other: Self, rm: RoundingMode) -> Ordering {
1742        let prec = max(self.significant_bits(), other.significant_bits());
1743        self.agm_prec_round_assign(other, prec, rm)
1744    }
1745
1746    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
1747    /// place, and rounding the result with the specified rounding mode. The [`Float`] on the
1748    /// right-hand side is taken by reference. An [`Ordering`] is returned, indicating whether the
1749    /// rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are not
1750    /// comparable to any [`Float`], whenever this function sets the [`Float`] to `NaN` it also
1751    /// returns `Equal`.
1752    ///
1753    /// The precision of the output is the maximum of the precision of the inputs. See
1754    /// [`RoundingMode`] for a description of the possible rounding modes.
1755    ///
1756    /// $$
1757    /// x \gets \text{AGM}(x,y)+\varepsilon
1758    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1759    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1760    /// $$
1761    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1762    ///   to be 0.
1763    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1764    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$, where $p$ is the maximum precision of the
1765    ///   inputs.
1766    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1767    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the
1768    ///   inputs.
1769    ///
1770    /// If the output has a precision, it is the maximum of the precisions of the inputs.
1771    ///
1772    /// See the [`Float::agm_round`] documentation for information on special cases, overflow, and
1773    /// underflow.
1774    ///
1775    /// If you want to specify an output precision, consider using
1776    /// [`Float::agm_prec_round_assign_ref`] instead. If you know you'll be using the `Nearest`
1777    /// rounding mode, consider using [`Float::agm_assign`] instead.
1778    ///
1779    /// # Worst-case complexity
1780    /// $T(n) = O(n (\log n)^2 \log\log n)$
1781    ///
1782    /// $M(n) = O(m)$
1783    ///
1784    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
1785    /// other.significant_bits())`, and $m$ is `other.significant_bits()`.
1786    ///
1787    /// # Panics
1788    /// Panics if `rm` is `Exact` but the two [`Float`] arguments are positive and distinct (and the
1789    /// exact result is therefore irrational).
1790    ///
1791    /// # Examples
1792    /// ```
1793    /// use malachite_base::rounding_modes::RoundingMode::*;
1794    /// use malachite_float::Float;
1795    /// use std::cmp::Ordering::*;
1796    ///
1797    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1798    /// assert_eq!(x.agm_round_assign_ref(&Float::from(6), Floor), Less);
1799    /// assert_eq!(x.to_string(), "13.458171481725615420766813156964");
1800    ///
1801    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1802    /// assert_eq!(x.agm_round_assign_ref(&Float::from(6), Ceiling), Greater);
1803    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
1804    ///
1805    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
1806    /// assert_eq!(x.agm_round_assign_ref(&Float::from(6), Nearest), Greater);
1807    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
1808    /// ```
1809    #[inline]
1810    pub fn agm_round_assign_ref(&mut self, other: &Self, rm: RoundingMode) -> Ordering {
1811        let prec = max(self.significant_bits(), other.significant_bits());
1812        self.agm_prec_round_assign_ref(other, prec, rm)
1813    }
1814
1815    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
1816    /// the specified precision and with the specified rounding mode, and returning the result as a
1817    /// [`Float`]. Both [`Rational`]s are taken by value. An [`Ordering`] is also returned,
1818    /// indicating whether the rounded AGM is less than, equal to, or greater than the exact AGM.
1819    /// Although `NaN`s are not comparable to any [`Float`], whenever this function returns a `NaN`
1820    /// it also returns `Equal`.
1821    ///
1822    /// See [`RoundingMode`] for a description of the possible rounding modes.
1823    ///
1824    /// $$
1825    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
1826    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1827    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1828    /// $$
1829    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1830    ///   to be 0.
1831    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1832    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
1833    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1834    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
1835    ///
1836    /// If the output has a precision, it is `prec`.
1837    ///
1838    /// Special cases:
1839    /// - $f(0,x,p,m)=f(x,0,p,m)=0.0$
1840    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
1841    ///
1842    /// Overflow and underflow:
1843    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
1844    ///   returned instead.
1845    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$
1846    ///   is returned instead, where `p` is the precision of the input.
1847    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor`, `Up`, or `Nearest`, $-\infty$ is
1848    ///   returned instead.
1849    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling` or `Down`,
1850    ///   $-(1-(1/2)^p)2^{2^{30}-1}$ is returned instead, where `p` is the precision of the input.
1851    /// - If $0<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
1852    /// - If $0<f(x,t,p,m)<2^{-2^{30}}$, and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned
1853    ///   instead.
1854    /// - If $0<f(x,y,p,m)\leq2^{-2^{30}-1}$, and $m$ is `Nearest`, $0.0$ is returned instead.
1855    /// - If $2^{-2^{30}-1}<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
1856    ///   instead.
1857    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Ceiling` or `Down`, $-0.0$ is returned
1858    ///   instead.
1859    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Floor` or `Up`, $-2^{-2^{30}}$ is returned
1860    ///   instead.
1861    /// - If $-2^{-2^{30}-1}\leq f(x,y,p,m)<0$, and $m$ is `Nearest`, $-0.0$ is returned instead.
1862    /// - If $-2^{-2^{30}}<f(x,y,p,m)<-2^{-2^{30}-1}$, and $m$ is `Nearest`, $-2^{-2^{30}}$ is
1863    ///   returned instead.
1864    ///
1865    /// If you know you'll be using `Nearest`, consider using [`Float::agm_rational_prec`] instead.
1866    ///
1867    /// # Worst-case complexity
1868    /// $T(n) = O(n (\log n)^2 \log\log n)$
1869    ///
1870    /// $M(n) = O(n \log n)$
1871    ///
1872    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1873    ///
1874    /// # Panics
1875    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
1876    /// the exact result is therefore irrational).
1877    ///
1878    /// # Examples
1879    /// ```
1880    /// use malachite_base::rounding_modes::RoundingMode::*;
1881    /// use malachite_float::Float;
1882    /// use malachite_q::Rational;
1883    /// use std::cmp::Ordering::*;
1884    ///
1885    /// let (agm, o) = Float::agm_rational_prec_round(
1886    ///     Rational::from_unsigneds(2u8, 3),
1887    ///     Rational::from_unsigneds(1u8, 5),
1888    ///     20,
1889    ///     Floor,
1890    /// );
1891    /// assert_eq!(agm.to_string(), "0.39851093");
1892    /// assert_eq!(o, Less);
1893    ///
1894    /// let (agm, o) = Float::agm_rational_prec_round(
1895    ///     Rational::from_unsigneds(2u8, 3),
1896    ///     Rational::from_unsigneds(1u8, 5),
1897    ///     20,
1898    ///     Ceiling,
1899    /// );
1900    /// assert_eq!(agm.to_string(), "0.39851141");
1901    /// assert_eq!(o, Greater);
1902    ///
1903    /// let (agm, o) = Float::agm_rational_prec_round(
1904    ///     Rational::from_unsigneds(2u8, 3),
1905    ///     Rational::from_unsigneds(1u8, 5),
1906    ///     20,
1907    ///     Nearest,
1908    /// );
1909    /// assert_eq!(agm.to_string(), "0.39851141");
1910    /// assert_eq!(o, Greater);
1911    /// ```
1912    #[allow(clippy::needless_pass_by_value)]
1913    #[inline]
1914    pub fn agm_rational_prec_round(
1915        x: Rational,
1916        y: Rational,
1917        prec: u64,
1918        rm: RoundingMode,
1919    ) -> (Self, Ordering) {
1920        Self::agm_rational_prec_round_val_ref(x, &y, prec, rm)
1921    }
1922
1923    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
1924    /// the specified precision and with the specified rounding mode, and returning the result as a
1925    /// [`Float`]. The first [`Rational`]s is taken by value and the second by reference. An
1926    /// [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to, or
1927    /// greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
1928    /// this function returns a `NaN` it also returns `Equal`.
1929    ///
1930    /// See [`RoundingMode`] for a description of the possible rounding modes.
1931    ///
1932    /// $$
1933    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
1934    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
1935    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
1936    /// $$
1937    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
1938    ///   to be 0.
1939    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
1940    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
1941    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1942    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
1943    ///
1944    /// If the output has a precision, it is `prec`.
1945    ///
1946    /// Special cases:
1947    /// - $f(0,x,p,m)=f(x,0,p,m)=0.0$
1948    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
1949    ///
1950    /// Overflow and underflow:
1951    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
1952    ///   returned instead.
1953    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$
1954    ///   is returned instead, where `p` is the precision of the input.
1955    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor`, `Up`, or `Nearest`, $-\infty$ is
1956    ///   returned instead.
1957    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling` or `Down`,
1958    ///   $-(1-(1/2)^p)2^{2^{30}-1}$ is returned instead, where `p` is the precision of the input.
1959    /// - If $0<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
1960    /// - If $0<f(x,t,p,m)<2^{-2^{30}}$, and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned
1961    ///   instead.
1962    /// - If $0<f(x,y,p,m)\leq2^{-2^{30}-1}$, and $m$ is `Nearest`, $0.0$ is returned instead.
1963    /// - If $2^{-2^{30}-1}<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
1964    ///   instead.
1965    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Ceiling` or `Down`, $-0.0$ is returned
1966    ///   instead.
1967    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Floor` or `Up`, $-2^{-2^{30}}$ is returned
1968    ///   instead.
1969    /// - If $-2^{-2^{30}-1}\leq f(x,y,p,m)<0$, and $m$ is `Nearest`, $-0.0$ is returned instead.
1970    /// - If $-2^{-2^{30}}<f(x,y,p,m)<-2^{-2^{30}-1}$, and $m$ is `Nearest`, $-2^{-2^{30}}$ is
1971    ///   returned instead.
1972    ///
1973    /// If you know you'll be using `Nearest`, consider using [`Float::agm_rational_prec_val_ref`]
1974    /// instead.
1975    ///
1976    /// # Worst-case complexity
1977    /// $T(n) = O(n (\log n)^2 \log\log n)$
1978    ///
1979    /// $M(n) = O(n \log n)$
1980    ///
1981    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1982    ///
1983    /// # Panics
1984    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
1985    /// the exact result is therefore irrational).
1986    ///
1987    /// # Examples
1988    /// ```
1989    /// use malachite_base::rounding_modes::RoundingMode::*;
1990    /// use malachite_float::Float;
1991    /// use malachite_q::Rational;
1992    /// use std::cmp::Ordering::*;
1993    ///
1994    /// let (agm, o) = Float::agm_rational_prec_round_val_ref(
1995    ///     Rational::from_unsigneds(2u8, 3),
1996    ///     &Rational::from_unsigneds(1u8, 5),
1997    ///     20,
1998    ///     Floor,
1999    /// );
2000    /// assert_eq!(agm.to_string(), "0.39851093");
2001    /// assert_eq!(o, Less);
2002    ///
2003    /// let (agm, o) = Float::agm_rational_prec_round_val_ref(
2004    ///     Rational::from_unsigneds(2u8, 3),
2005    ///     &Rational::from_unsigneds(1u8, 5),
2006    ///     20,
2007    ///     Ceiling,
2008    /// );
2009    /// assert_eq!(agm.to_string(), "0.39851141");
2010    /// assert_eq!(o, Greater);
2011    ///
2012    /// let (agm, o) = Float::agm_rational_prec_round_val_ref(
2013    ///     Rational::from_unsigneds(2u8, 3),
2014    ///     &Rational::from_unsigneds(1u8, 5),
2015    ///     20,
2016    ///     Nearest,
2017    /// );
2018    /// assert_eq!(agm.to_string(), "0.39851141");
2019    /// assert_eq!(o, Greater);
2020    /// ```
2021    pub fn agm_rational_prec_round_val_ref(
2022        x: Rational,
2023        y: &Rational,
2024        prec: u64,
2025        rm: RoundingMode,
2026    ) -> (Self, Ordering) {
2027        assert_ne!(prec, 0);
2028        match (x.sign(), y.sign()) {
2029            (Equal, _) | (_, Equal) => return (float_zero!(), Equal),
2030            (Less, _) | (_, Less) => return (float_nan!(), Equal),
2031            _ => {}
2032        }
2033        if x == *y {
2034            return Self::from_rational_prec_round(x, prec, rm);
2035        }
2036        assert_ne!(rm, Exact, "Inexact AGM");
2037        let x_exp = i32::saturating_from(x.floor_log_base_2_abs()).saturating_add(1);
2038        let y_exp = i32::saturating_from(y.floor_log_base_2_abs()).saturating_add(1);
2039        let x_overflow = x_exp > Self::MAX_EXPONENT;
2040        let y_overflow = y_exp > Self::MAX_EXPONENT;
2041        let x_underflow = x_exp < Self::MIN_EXPONENT;
2042        let y_underflow = y_exp < Self::MIN_EXPONENT;
2043        match (x_overflow, y_overflow, x_underflow, y_underflow) {
2044            (true, true, _, _) => Self::from_rational_prec_round(x, prec, rm),
2045            (_, _, true, true)
2046                if rm != Nearest
2047                    || x_exp < Self::MIN_EXPONENT_MINUS_1 && y_exp < Self::MIN_EXPONENT_MINUS_1 =>
2048            {
2049                Self::from_rational_prec_round(x, prec, rm)
2050            }
2051            (false, false, false, false)
2052                if x_exp < Self::MAX_EXPONENT && y_exp < Self::MAX_EXPONENT =>
2053            {
2054                agm_rational_helper(&x, y, prec, rm)
2055            }
2056            _ => agm_rational_helper_extended(&x, y, prec, rm),
2057        }
2058    }
2059
2060    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2061    /// the specified precision and with the specified rounding mode, and returning the result as a
2062    /// [`Float`]. The first [`Rational`]s is taken by reference and the second by value. An
2063    /// [`Ordering`] is also returned, indicating whether the rounded AGM is less than, equal to, or
2064    /// greater than the exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever
2065    /// this function returns a `NaN` it also returns `Equal`.
2066    ///
2067    /// See [`RoundingMode`] for a description of the possible rounding modes.
2068    ///
2069    /// $$
2070    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
2071    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2072    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2073    /// $$
2074    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2075    ///   to be 0.
2076    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2077    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2078    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2079    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2080    ///
2081    /// If the output has a precision, it is `prec`.
2082    ///
2083    /// Special cases:
2084    /// - $f(0,x,p,m)=f(x,0,p,m)=0.0$
2085    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
2086    ///
2087    /// Overflow and underflow:
2088    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
2089    ///   returned instead.
2090    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$
2091    ///   is returned instead, where `p` is the precision of the input.
2092    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor`, `Up`, or `Nearest`, $-\infty$ is
2093    ///   returned instead.
2094    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling` or `Down`,
2095    ///   $-(1-(1/2)^p)2^{2^{30}-1}$ is returned instead, where `p` is the precision of the input.
2096    /// - If $0<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
2097    /// - If $0<f(x,t,p,m)<2^{-2^{30}}$, and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned
2098    ///   instead.
2099    /// - If $0<f(x,y,p,m)\leq2^{-2^{30}-1}$, and $m$ is `Nearest`, $0.0$ is returned instead.
2100    /// - If $2^{-2^{30}-1}<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
2101    ///   instead.
2102    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Ceiling` or `Down`, $-0.0$ is returned
2103    ///   instead.
2104    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Floor` or `Up`, $-2^{-2^{30}}$ is returned
2105    ///   instead.
2106    /// - If $-2^{-2^{30}-1}\leq f(x,y,p,m)<0$, and $m$ is `Nearest`, $-0.0$ is returned instead.
2107    /// - If $-2^{-2^{30}}<f(x,y,p,m)<-2^{-2^{30}-1}$, and $m$ is `Nearest`, $-2^{-2^{30}}$ is
2108    ///   returned instead.
2109    ///
2110    /// If you know you'll be using `Nearest`, consider using [`Float::agm_rational_prec_ref_val`]
2111    /// instead.
2112    ///
2113    /// # Worst-case complexity
2114    /// $T(n) = O(n (\log n)^2 \log\log n)$
2115    ///
2116    /// $M(n) = O(n \log n)$
2117    ///
2118    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2119    ///
2120    /// # Panics
2121    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2122    /// the exact result is therefore irrational).
2123    ///
2124    /// # Examples
2125    /// ```
2126    /// use malachite_base::rounding_modes::RoundingMode::*;
2127    /// use malachite_float::Float;
2128    /// use malachite_q::Rational;
2129    /// use std::cmp::Ordering::*;
2130    ///
2131    /// let (agm, o) = Float::agm_rational_prec_round_ref_val(
2132    ///     &Rational::from_unsigneds(2u8, 3),
2133    ///     Rational::from_unsigneds(1u8, 5),
2134    ///     20,
2135    ///     Floor,
2136    /// );
2137    /// assert_eq!(agm.to_string(), "0.39851093");
2138    /// assert_eq!(o, Less);
2139    ///
2140    /// let (agm, o) = Float::agm_rational_prec_round_ref_val(
2141    ///     &Rational::from_unsigneds(2u8, 3),
2142    ///     Rational::from_unsigneds(1u8, 5),
2143    ///     20,
2144    ///     Ceiling,
2145    /// );
2146    /// assert_eq!(agm.to_string(), "0.39851141");
2147    /// assert_eq!(o, Greater);
2148    ///
2149    /// let (agm, o) = Float::agm_rational_prec_round_ref_val(
2150    ///     &Rational::from_unsigneds(2u8, 3),
2151    ///     Rational::from_unsigneds(1u8, 5),
2152    ///     20,
2153    ///     Nearest,
2154    /// );
2155    /// assert_eq!(agm.to_string(), "0.39851141");
2156    /// assert_eq!(o, Greater);
2157    /// ```
2158    pub fn agm_rational_prec_round_ref_val(
2159        x: &Rational,
2160        y: Rational,
2161        prec: u64,
2162        rm: RoundingMode,
2163    ) -> (Self, Ordering) {
2164        assert_ne!(prec, 0);
2165        match (x.sign(), y.sign()) {
2166            (Equal, _) | (_, Equal) => return (float_zero!(), Equal),
2167            (Less, _) | (_, Less) => return (float_nan!(), Equal),
2168            _ => {}
2169        }
2170        if *x == y {
2171            return Self::from_rational_prec_round(y, prec, rm);
2172        }
2173        assert_ne!(rm, Exact, "Inexact AGM");
2174        let x_exp = i32::saturating_from(x.floor_log_base_2_abs()).saturating_add(1);
2175        let y_exp = i32::saturating_from(y.floor_log_base_2_abs()).saturating_add(1);
2176        let x_overflow = x_exp > Self::MAX_EXPONENT;
2177        let y_overflow = y_exp > Self::MAX_EXPONENT;
2178        let x_underflow = x_exp < Self::MIN_EXPONENT;
2179        let y_underflow = y_exp < Self::MIN_EXPONENT;
2180        match (x_overflow, y_overflow, x_underflow, y_underflow) {
2181            (true, true, _, _) => Self::from_rational_prec_round(y, prec, rm),
2182            (_, _, true, true)
2183                if rm != Nearest
2184                    || x_exp < Self::MIN_EXPONENT_MINUS_1 && y_exp < Self::MIN_EXPONENT_MINUS_1 =>
2185            {
2186                Self::from_rational_prec_round(y, prec, rm)
2187            }
2188            (false, false, false, false)
2189                if x_exp < Self::MAX_EXPONENT && y_exp < Self::MAX_EXPONENT =>
2190            {
2191                agm_rational_helper(x, &y, prec, rm)
2192            }
2193            _ => agm_rational_helper_extended(x, &y, prec, rm),
2194        }
2195    }
2196
2197    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2198    /// the specified precision and with the specified rounding mode, and returning the result as a
2199    /// [`Float`]. Both [`Rational`]s are taken by reference. An [`Ordering`] is also returned,
2200    /// indicating whether the rounded AGM is less than, equal to, or greater than the exact AGM.
2201    /// Although `NaN`s are not comparable to any [`Float`], whenever this function returns a `NaN`
2202    /// it also returns `Equal`.
2203    ///
2204    /// See [`RoundingMode`] for a description of the possible rounding modes.
2205    ///
2206    /// $$
2207    /// f(x,y,p,m) = \text{AGM}(x,y)+\varepsilon
2208    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2209    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2210    /// $$
2211    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2212    ///   to be 0.
2213    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2214    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2215    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2216    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2217    ///
2218    /// If the output has a precision, it is `prec`.
2219    ///
2220    /// Special cases:
2221    /// - $f(0,x,p,m)=f(x,0,p,m)=0.0$
2222    /// - $f(x,y,p,m)=\text{NaN}$ if $x<0$ or $y<0$
2223    ///
2224    /// Overflow and underflow:
2225    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
2226    ///   returned instead.
2227    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$
2228    ///   is returned instead, where `p` is the precision of the input.
2229    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor`, `Up`, or `Nearest`, $-\infty$ is
2230    ///   returned instead.
2231    /// - If $f(x,y,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling` or `Down`,
2232    ///   $-(1-(1/2)^p)2^{2^{30}-1}$ is returned instead, where `p` is the precision of the input.
2233    /// - If $0<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
2234    /// - If $0<f(x,t,p,m)<2^{-2^{30}}$, and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned
2235    ///   instead.
2236    /// - If $0<f(x,y,p,m)\leq2^{-2^{30}-1}$, and $m$ is `Nearest`, $0.0$ is returned instead.
2237    /// - If $2^{-2^{30}-1}<f(x,y,p,m)<2^{-2^{30}}$, and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
2238    ///   instead.
2239    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Ceiling` or `Down`, $-0.0$ is returned
2240    ///   instead.
2241    /// - If $-2^{-2^{30}}<f(x,y,p,m)<0$, and $m$ is `Floor` or `Up`, $-2^{-2^{30}}$ is returned
2242    ///   instead.
2243    /// - If $-2^{-2^{30}-1}\leq f(x,y,p,m)<0$, and $m$ is `Nearest`, $-0.0$ is returned instead.
2244    /// - If $-2^{-2^{30}}<f(x,y,p,m)<-2^{-2^{30}-1}$, and $m$ is `Nearest`, $-2^{-2^{30}}$ is
2245    ///   returned instead.
2246    ///
2247    /// If you know you'll be using `Nearest`, consider using [`Float::agm_rational_prec_ref_ref`]
2248    /// instead.
2249    ///
2250    /// # Worst-case complexity
2251    /// $T(n) = O(n (\log n)^2 \log\log n)$
2252    ///
2253    /// $M(n) = O(n \log n)$
2254    ///
2255    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2256    ///
2257    /// # Panics
2258    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2259    /// the exact result is therefore irrational).
2260    ///
2261    /// # Examples
2262    /// ```
2263    /// use malachite_base::rounding_modes::RoundingMode::*;
2264    /// use malachite_float::Float;
2265    /// use malachite_q::Rational;
2266    /// use std::cmp::Ordering::*;
2267    ///
2268    /// let (agm, o) = Float::agm_rational_prec_round_ref_ref(
2269    ///     &Rational::from_unsigneds(2u8, 3),
2270    ///     &Rational::from_unsigneds(1u8, 5),
2271    ///     20,
2272    ///     Floor,
2273    /// );
2274    /// assert_eq!(agm.to_string(), "0.39851093");
2275    /// assert_eq!(o, Less);
2276    ///
2277    /// let (agm, o) = Float::agm_rational_prec_round_ref_ref(
2278    ///     &Rational::from_unsigneds(2u8, 3),
2279    ///     &Rational::from_unsigneds(1u8, 5),
2280    ///     20,
2281    ///     Ceiling,
2282    /// );
2283    /// assert_eq!(agm.to_string(), "0.39851141");
2284    /// assert_eq!(o, Greater);
2285    ///
2286    /// let (agm, o) = Float::agm_rational_prec_round_ref_ref(
2287    ///     &Rational::from_unsigneds(2u8, 3),
2288    ///     &Rational::from_unsigneds(1u8, 5),
2289    ///     20,
2290    ///     Nearest,
2291    /// );
2292    /// assert_eq!(agm.to_string(), "0.39851141");
2293    /// assert_eq!(o, Greater);
2294    /// ```
2295    pub fn agm_rational_prec_round_ref_ref(
2296        x: &Rational,
2297        y: &Rational,
2298        prec: u64,
2299        rm: RoundingMode,
2300    ) -> (Self, Ordering) {
2301        assert_ne!(prec, 0);
2302        match (x.sign(), y.sign()) {
2303            (Equal, _) | (_, Equal) => return (float_zero!(), Equal),
2304            (Less, _) | (_, Less) => return (float_nan!(), Equal),
2305            _ => {}
2306        }
2307        if x == y {
2308            return Self::from_rational_prec_round_ref(x, prec, rm);
2309        }
2310        assert_ne!(rm, Exact, "Inexact AGM");
2311        let x_exp = i32::saturating_from(x.floor_log_base_2_abs()).saturating_add(1);
2312        let y_exp = i32::saturating_from(y.floor_log_base_2_abs()).saturating_add(1);
2313        let x_overflow = x_exp > Self::MAX_EXPONENT;
2314        let y_overflow = y_exp > Self::MAX_EXPONENT;
2315        let x_underflow = x_exp < Self::MIN_EXPONENT;
2316        let y_underflow = y_exp < Self::MIN_EXPONENT;
2317        match (x_overflow, y_overflow, x_underflow, y_underflow) {
2318            (true, true, _, _) => Self::from_rational_prec_round_ref(x, prec, rm),
2319            (_, _, true, true)
2320                if rm != Nearest
2321                    || x_exp < Self::MIN_EXPONENT_MINUS_1 && y_exp < Self::MIN_EXPONENT_MINUS_1 =>
2322            {
2323                Self::from_rational_prec_round_ref(x, prec, rm)
2324            }
2325            (false, false, false, false)
2326                if x_exp < Self::MAX_EXPONENT && y_exp < Self::MAX_EXPONENT =>
2327            {
2328                agm_rational_helper(x, y, prec, rm)
2329            }
2330            _ => agm_rational_helper_extended(x, y, prec, rm),
2331        }
2332    }
2333
2334    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2335    /// the nearest value of the specified precision, and returning the result as a [`Float`]. Both
2336    /// [`Rational`]s are taken by value. An [`Ordering`] is also returned, indicating whether the
2337    /// rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are not
2338    /// comparable to any [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
2339    ///
2340    /// See [`RoundingMode`] for a description of the possible rounding modes.
2341    ///
2342    /// $$
2343    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
2344    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2345    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2346    /// $$
2347    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2348    ///   to be 0.
2349    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2350    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2351    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2352    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2353    ///
2354    /// If the output has a precision, it is `prec`.
2355    ///
2356    /// Special cases:
2357    /// - $f(0,x,p)=f(x,0,p)=0.0$
2358    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
2359    ///
2360    /// Overflow and underflow:
2361    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
2362    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Up`, $-\infty$ is returned instead.
2363    /// - If $0<f(x,y,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
2364    /// - If $2^{-2^{30}-1}<f(x,y,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
2365    /// - If $-2^{-2^{30}-1}\leq f(x,y,p)<0$, $-0.0$ is returned instead.
2366    /// - If $-2^{-2^{30}}<f(x,y,p)<-2^{-2^{30}-1}$, $-2^{-2^{30}}$ is returned instead.
2367    ///
2368    /// If you want to use a rounding mode other than `Nearest`, consider using
2369    /// [`Float::agm_rational_prec_round`] instead.
2370    ///
2371    /// # Worst-case complexity
2372    /// $T(n) = O(n (\log n)^2 \log\log n)$
2373    ///
2374    /// $M(n) = O(n \log n)$
2375    ///
2376    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2377    ///
2378    /// # Panics
2379    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2380    /// the exact result is therefore irrational).
2381    ///
2382    /// # Examples
2383    /// ```
2384    /// use malachite_float::Float;
2385    /// use malachite_q::Rational;
2386    /// use std::cmp::Ordering::*;
2387    ///
2388    /// let (agm, o) = Float::agm_rational_prec(
2389    ///     Rational::from_unsigneds(2u8, 3),
2390    ///     Rational::from_unsigneds(1u8, 5),
2391    ///     20,
2392    /// );
2393    /// assert_eq!(agm.to_string(), "0.39851141");
2394    /// assert_eq!(o, Greater);
2395    /// ```
2396    #[allow(clippy::needless_pass_by_value)]
2397    #[inline]
2398    pub fn agm_rational_prec(x: Rational, y: Rational, prec: u64) -> (Self, Ordering) {
2399        Self::agm_rational_prec_round_val_ref(x, &y, prec, Nearest)
2400    }
2401
2402    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2403    /// the nearest value of the specified precision, and returning the result as a [`Float`]. The
2404    /// first [`Rational`] is taken by value and the second by reference. An [`Ordering`] is also
2405    /// returned, indicating whether the rounded AGM is less than, equal to, or greater than the
2406    /// exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever this function
2407    /// returns a `NaN` it also returns `Equal`.
2408    ///
2409    /// See [`RoundingMode`] for a description of the possible rounding modes.
2410    ///
2411    /// $$
2412    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
2413    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2414    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2415    /// $$
2416    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2417    ///   to be 0.
2418    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2419    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2420    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2421    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2422    ///
2423    /// If the output has a precision, it is `prec`.
2424    ///
2425    /// Special cases:
2426    /// - $f(0,x,p)=f(x,0,p)=0.0$
2427    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
2428    ///
2429    /// Overflow and underflow:
2430    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
2431    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Up`, $-\infty$ is returned instead.
2432    /// - If $0<f(x,y,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
2433    /// - If $2^{-2^{30}-1}<f(x,y,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
2434    /// - If $-2^{-2^{30}-1}\leq f(x,y,p)<0$, $-0.0$ is returned instead.
2435    /// - If $-2^{-2^{30}}<f(x,y,p)<-2^{-2^{30}-1}$, $-2^{-2^{30}}$ is returned instead.
2436    ///
2437    /// If you want to use a rounding mode other than `Nearest`, consider using
2438    /// [`Float::agm_rational_prec_round_val_ref`] instead.
2439    ///
2440    /// # Worst-case complexity
2441    /// $T(n) = O(n (\log n)^2 \log\log n)$
2442    ///
2443    /// $M(n) = O(n \log n)$
2444    ///
2445    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2446    ///
2447    /// # Panics
2448    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2449    /// the exact result is therefore irrational).
2450    ///
2451    /// # Examples
2452    /// ```
2453    /// use malachite_float::Float;
2454    /// use malachite_q::Rational;
2455    /// use std::cmp::Ordering::*;
2456    ///
2457    /// let (agm, o) = Float::agm_rational_prec_val_ref(
2458    ///     Rational::from_unsigneds(2u8, 3),
2459    ///     &Rational::from_unsigneds(1u8, 5),
2460    ///     20,
2461    /// );
2462    /// assert_eq!(agm.to_string(), "0.39851141");
2463    /// assert_eq!(o, Greater);
2464    /// ```
2465    #[inline]
2466    pub fn agm_rational_prec_val_ref(x: Rational, y: &Rational, prec: u64) -> (Self, Ordering) {
2467        Self::agm_rational_prec_round_val_ref(x, y, prec, Nearest)
2468    }
2469
2470    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2471    /// the nearest value of the specified precision, and returning the result as a [`Float`]. The
2472    /// first [`Rational`] is taken by reference and the second by value. An [`Ordering`] is also
2473    /// returned, indicating whether the rounded AGM is less than, equal to, or greater than the
2474    /// exact AGM. Although `NaN`s are not comparable to any [`Float`], whenever this function
2475    /// returns a `NaN` it also returns `Equal`.
2476    ///
2477    /// See [`RoundingMode`] for a description of the possible rounding modes.
2478    ///
2479    /// $$
2480    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
2481    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2482    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2483    /// $$
2484    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2485    ///   to be 0.
2486    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2487    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2488    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2489    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2490    ///
2491    /// If the output has a precision, it is `prec`.
2492    ///
2493    /// Special cases:
2494    /// - $f(0,x,p)=f(x,0,p)=0.0$
2495    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
2496    ///
2497    /// Overflow and underflow:
2498    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
2499    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Up`, $-\infty$ is returned instead.
2500    /// - If $0<f(x,y,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
2501    /// - If $2^{-2^{30}-1}<f(x,y,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
2502    /// - If $-2^{-2^{30}-1}\leq f(x,y,p)<0$, $-0.0$ is returned instead.
2503    /// - If $-2^{-2^{30}}<f(x,y,p)<-2^{-2^{30}-1}$, $-2^{-2^{30}}$ is returned instead.
2504    ///
2505    /// If you want to use a rounding mode other than `Nearest`, consider using
2506    /// [`Float::agm_rational_prec_round_ref_val`] instead.
2507    ///
2508    /// # Worst-case complexity
2509    /// $T(n) = O(n (\log n)^2 \log\log n)$
2510    ///
2511    /// $M(n) = O(n \log n)$
2512    ///
2513    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2514    ///
2515    /// # Panics
2516    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2517    /// the exact result is therefore irrational).
2518    ///
2519    /// # Examples
2520    /// ```
2521    /// use malachite_float::Float;
2522    /// use malachite_q::Rational;
2523    /// use std::cmp::Ordering::*;
2524    ///
2525    /// let (agm, o) = Float::agm_rational_prec_ref_val(
2526    ///     &Rational::from_unsigneds(2u8, 3),
2527    ///     Rational::from_unsigneds(1u8, 5),
2528    ///     20,
2529    /// );
2530    /// assert_eq!(agm.to_string(), "0.39851141");
2531    /// assert_eq!(o, Greater);
2532    /// ```
2533    #[inline]
2534    pub fn agm_rational_prec_ref_val(x: &Rational, y: Rational, prec: u64) -> (Self, Ordering) {
2535        Self::agm_rational_prec_round_ref_val(x, y, prec, Nearest)
2536    }
2537
2538    /// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, rounding the result to
2539    /// the nearest value of the specified precision, and returning the result as a [`Float`]. Both
2540    /// [`Rational`]s are taken by reference. An [`Ordering`] is also returned, indicating whether
2541    /// the rounded AGM is less than, equal to, or greater than the exact AGM. Although `NaN`s are
2542    /// not comparable to any [`Float`], whenever this function returns a `NaN` it also returns
2543    /// `Equal`.
2544    ///
2545    /// See [`RoundingMode`] for a description of the possible rounding modes.
2546    ///
2547    /// $$
2548    /// f(x,y,p) = \text{AGM}(x,y)+\varepsilon
2549    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2550    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2551    /// $$
2552    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2553    ///   to be 0.
2554    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon|
2555    ///   < 2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p+1}$.
2556    /// - If $\text{AGM}(x,y)$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
2557    ///   2^{\lfloor\log_2 \text{AGM}(x,y)\rfloor-p}$.
2558    ///
2559    /// If the output has a precision, it is `prec`.
2560    ///
2561    /// Special cases:
2562    /// - $f(0,x,p)=f(x,0,p)=0.0$
2563    /// - $f(x,y,p)=\text{NaN}$ if $x<0$ or $y<0$
2564    ///
2565    /// Overflow and underflow:
2566    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
2567    /// - If $f(x,y,p)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Up`, $-\infty$ is returned instead.
2568    /// - If $0<f(x,y,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
2569    /// - If $2^{-2^{30}-1}<f(x,y,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
2570    /// - If $-2^{-2^{30}-1}\leq f(x,y,p)<0$, $-0.0$ is returned instead.
2571    /// - If $-2^{-2^{30}}<f(x,y,p)<-2^{-2^{30}-1}$, $-2^{-2^{30}}$ is returned instead.
2572    ///
2573    /// If you want to use a rounding mode other than `Nearest`, consider using
2574    /// [`Float::agm_rational_prec_round_ref_ref`] instead.
2575    ///
2576    /// # Worst-case complexity
2577    /// $T(n) = O(n (\log n)^2 \log\log n)$
2578    ///
2579    /// $M(n) = O(n \log n)$
2580    ///
2581    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
2582    ///
2583    /// # Panics
2584    /// Panics if `rm` is `Exact` but the two [`Rational`] arguments are positive and distinct (and
2585    /// the exact result is therefore irrational).
2586    ///
2587    /// # Examples
2588    /// ```
2589    /// use malachite_float::Float;
2590    /// use malachite_q::Rational;
2591    /// use std::cmp::Ordering::*;
2592    ///
2593    /// let (agm, o) = Float::agm_rational_prec_ref_ref(
2594    ///     &Rational::from_unsigneds(2u8, 3),
2595    ///     &Rational::from_unsigneds(1u8, 5),
2596    ///     20,
2597    /// );
2598    /// assert_eq!(agm.to_string(), "0.39851141");
2599    /// assert_eq!(o, Greater);
2600    /// ```
2601    #[inline]
2602    pub fn agm_rational_prec_ref_ref(x: &Rational, y: &Rational, prec: u64) -> (Self, Ordering) {
2603        Self::agm_rational_prec_round_ref_ref(x, y, prec, Nearest)
2604    }
2605}
2606
2607impl Agm<Self> for Float {
2608    type Output = Self;
2609
2610    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, taking both by value.
2611    ///
2612    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2613    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2614    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2615    /// rounding mode.
2616    ///
2617    /// $$
2618    /// f(x,y) = \text{AGM}(x,y)+\varepsilon
2619    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2620    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2621    /// $$
2622    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2623    ///   to be 0.
2624    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2625    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2626    ///
2627    /// Special cases:
2628    /// - $f(\text{NaN},x)=f(x,\text{NaN})=f(-\infty,x)=f(x,-\infty)=\text{NaN}$
2629    /// - $f(\infty,x)=f(x,\infty)=\text{NaN}$ if $x\neq\infty$
2630    /// - $f(\infty,\infty)=\infty$
2631    /// - $f(\pm0.0,x)=f(x,\pm0.0)=0.0$
2632    /// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
2633    ///
2634    /// Neither overflow nor underflow is possible.
2635    ///
2636    /// If you want to use a rounding mode other than `Nearest`, consider using [`Float::agm_prec`]
2637    /// instead. If you want to specify the output precision, consider using [`Float::agm_round`].
2638    /// If you want both of these things, consider using [`Float::agm_prec_round`].
2639    ///
2640    /// # Worst-case complexity
2641    /// $T(n) = O(n (\log n)^2 \log\log n)$
2642    ///
2643    /// $M(n) = O(n \log n)$
2644    ///
2645    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
2646    /// other.significant_bits())`.
2647    ///
2648    /// # Examples
2649    /// ```
2650    /// use malachite_base::num::arithmetic::traits::Agm;
2651    /// use malachite_float::Float;
2652    ///
2653    /// assert_eq!(
2654    ///     Float::from_unsigned_prec(24u8, 100)
2655    ///         .0
2656    ///         .agm(Float::from(6))
2657    ///         .to_string(),
2658    ///     "13.458171481725615420766813156976"
2659    /// );
2660    /// ```
2661    #[inline]
2662    fn agm(self, other: Self) -> Self {
2663        let prec = max(self.significant_bits(), other.significant_bits());
2664        self.agm_prec_round(other, prec, Nearest).0
2665    }
2666}
2667
2668impl Agm<&Self> for Float {
2669    type Output = Self;
2670
2671    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, taking the first by value
2672    /// and the second by reference.
2673    ///
2674    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2675    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2676    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2677    /// rounding mode.
2678    ///
2679    /// $$
2680    /// f(x,y) = \text{AGM}(x,y)+\varepsilon
2681    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2682    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2683    /// $$
2684    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2685    ///   to be 0.
2686    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2687    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2688    ///
2689    /// Special cases:
2690    /// - $f(\text{NaN},x)=f(x,\text{NaN})=f(-\infty,x)=f(x,-\infty)=\text{NaN}$
2691    /// - $f(\infty,x)=f(x,\infty)=\text{NaN}$ if $x\neq\infty$
2692    /// - $f(\infty,\infty)=\infty$
2693    /// - $f(\pm0.0,x)=f(x,\pm0.0)=0.0$
2694    /// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
2695    ///
2696    /// Neither overflow nor underflow is possible.
2697    ///
2698    /// If you want to use a rounding mode other than `Nearest`, consider using
2699    /// [`Float::agm_prec_val_ref`] instead. If you want to specify the output precision, consider
2700    /// using [`Float::agm_round_val_ref`]. If you want both of these things, consider using
2701    /// [`Float::agm_prec_round_val_ref`].
2702    ///
2703    /// # Worst-case complexity
2704    /// $T(n) = O(n (\log n)^2 \log\log n)$
2705    ///
2706    /// $M(n) = O(m)$
2707    ///
2708    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
2709    /// other.significant_bits())`, and $m$ is `other.significant_bits()`.
2710    ///
2711    /// # Examples
2712    /// ```
2713    /// use malachite_base::num::arithmetic::traits::Agm;
2714    /// use malachite_float::Float;
2715    ///
2716    /// assert_eq!(
2717    ///     Float::from_unsigned_prec(24u8, 100)
2718    ///         .0
2719    ///         .agm(&Float::from(6))
2720    ///         .to_string(),
2721    ///     "13.458171481725615420766813156976"
2722    /// );
2723    /// ```
2724    #[inline]
2725    fn agm(self, other: &Self) -> Self {
2726        let prec = max(self.significant_bits(), other.significant_bits());
2727        self.agm_prec_round_val_ref(other, prec, Nearest).0
2728    }
2729}
2730
2731impl Agm<Float> for &Float {
2732    type Output = Float;
2733
2734    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, taking the first by
2735    /// reference and the second by value.
2736    ///
2737    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2738    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2739    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2740    /// rounding mode.
2741    ///
2742    /// $$
2743    /// f(x,y) = \text{AGM}(x,y)+\varepsilon
2744    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2745    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2746    /// $$
2747    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2748    ///   to be 0.
2749    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2750    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2751    ///
2752    /// Special cases:
2753    /// - $f(\text{NaN},x)=f(x,\text{NaN})=f(-\infty,x)=f(x,-\infty)=\text{NaN}$
2754    /// - $f(\infty,x)=f(x,\infty)=\text{NaN}$ if $x\neq\infty$
2755    /// - $f(\infty,\infty)=\infty$
2756    /// - $f(\pm0.0,x)=f(x,\pm0.0)=0.0$
2757    /// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
2758    ///
2759    /// Neither overflow nor underflow is possible.
2760    ///
2761    /// If you want to use a rounding mode other than `Nearest`, consider using
2762    /// [`Float::agm_prec_ref_val`] instead. If you want to specify the output precision, consider
2763    /// using [`Float::agm_round_ref_val`]. If you want both of these things, consider using
2764    /// [`Float::agm_prec_round_ref_val`].
2765    ///
2766    /// # Worst-case complexity
2767    /// $T(n) = O(n (\log n)^2 \log\log n)$
2768    ///
2769    /// $M(n) = O(m)$
2770    ///
2771    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
2772    /// other.significant_bits())`, and $m$ is `self.significant_bits()`.
2773    ///
2774    /// # Examples
2775    /// ```
2776    /// use malachite_base::num::arithmetic::traits::Agm;
2777    /// use malachite_float::Float;
2778    ///
2779    /// assert_eq!(
2780    ///     (&Float::from_unsigned_prec(24u8, 100).0)
2781    ///         .agm(Float::from(6))
2782    ///         .to_string(),
2783    ///     "13.458171481725615420766813156976"
2784    /// );
2785    /// ```
2786    #[inline]
2787    fn agm(self, other: Float) -> Float {
2788        let prec = max(self.significant_bits(), other.significant_bits());
2789        self.agm_prec_round_ref_val(other, prec, Nearest).0
2790    }
2791}
2792
2793impl Agm<&Float> for &Float {
2794    type Output = Float;
2795
2796    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, taking both by reference.
2797    ///
2798    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2799    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2800    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2801    /// rounding mode.
2802    ///
2803    /// $$
2804    /// f(x,y) = \text{AGM}(x,y)+\varepsilon
2805    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2806    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2807    /// $$
2808    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2809    ///   to be 0.
2810    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2811    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2812    ///
2813    /// Special cases:
2814    /// - $f(\text{NaN},x)=f(x,\text{NaN})=f(-\infty,x)=f(x,-\infty)=\text{NaN}$
2815    /// - $f(\infty,x)=f(x,\infty)=\text{NaN}$ if $x\neq\infty$
2816    /// - $f(\infty,\infty)=\infty$
2817    /// - $f(\pm0.0,x)=f(x,\pm0.0)=0.0$
2818    /// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
2819    ///
2820    /// Neither overflow nor underflow is possible.
2821    ///
2822    /// If you want to use a rounding mode other than `Nearest`, consider using
2823    /// [`Float::agm_prec_ref_ref`] instead. If you want to specify the output precision, consider
2824    /// using [`Float::agm_round_ref_ref`]. If you want both of these things, consider using
2825    /// [`Float::agm_prec_round_ref_ref`].
2826    ///
2827    /// # Worst-case complexity
2828    /// $T(n) = O(n (\log n)^2 \log\log n)$
2829    ///
2830    /// $M(n) = O(n \log n)$
2831    ///
2832    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
2833    /// other.significant_bits())`.
2834    ///
2835    /// # Examples
2836    /// ```
2837    /// use malachite_base::num::arithmetic::traits::Agm;
2838    /// use malachite_float::Float;
2839    ///
2840    /// assert_eq!(
2841    ///     (&Float::from_unsigned_prec(24u8, 100).0)
2842    ///         .agm(&Float::from(6))
2843    ///         .to_string(),
2844    ///     "13.458171481725615420766813156976"
2845    /// );
2846    /// ```
2847    #[inline]
2848    fn agm(self, other: &Float) -> Float {
2849        let prec = max(self.significant_bits(), other.significant_bits());
2850        self.agm_prec_round_ref_ref(other, prec, Nearest).0
2851    }
2852}
2853
2854impl AgmAssign<Self> for Float {
2855    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
2856    /// place, and taking the [`Float`] on the right-hand side by value.
2857    ///
2858    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2859    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2860    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2861    /// rounding mode.
2862    ///
2863    /// $$
2864    /// x\gets = \text{AGM}(x,y)+\varepsilon
2865    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2866    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2867    /// $$
2868    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2869    ///   to be 0.
2870    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2871    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2872    ///
2873    /// See the [`Float::agm`] documentation for information on special cases, overflow, and
2874    /// underflow.
2875    ///
2876    /// If you want to use a rounding mode other than `Nearest`, consider using
2877    /// [`Float::agm_prec_assign`] instead. If you want to specify the output precision, consider
2878    /// using [`Float::agm_round_assign`]. If you want both of these things, consider using
2879    /// [`Float::agm_prec_round_assign`].
2880    ///
2881    /// # Worst-case complexity
2882    /// $T(n) = O(n (\log n)^2 \log\log n)$
2883    ///
2884    /// $M(n) = O(n \log n)$
2885    ///
2886    /// where $T$ is time, $M$ is additional memory, and $n$ is `max(self.significant_bits(),
2887    /// other.significant_bits())`.
2888    ///
2889    /// # Examples
2890    /// ```
2891    /// use malachite_base::num::arithmetic::traits::AgmAssign;
2892    /// use malachite_float::Float;
2893    ///
2894    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
2895    /// x.agm_assign(Float::from(6));
2896    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
2897    /// ```
2898    #[inline]
2899    fn agm_assign(&mut self, other: Self) {
2900        let prec = max(self.significant_bits(), other.significant_bits());
2901        self.agm_prec_round_assign(other, prec, Nearest);
2902    }
2903}
2904
2905impl AgmAssign<&Self> for Float {
2906    /// Computes the arithmetic-geometric mean (AGM) of two [`Float`]s, mutating the first one in
2907    /// place, and taking the [`Float`] on the right-hand side by reference.
2908    ///
2909    /// If the output has a precision, it is the maximum of the precisions of the inputs. If the agm
2910    /// is equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s
2911    /// in its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
2912    /// rounding mode.
2913    ///
2914    /// $$
2915    /// x\gets = \text{AGM}(x,y)+\varepsilon
2916    /// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2917    /// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2918    /// $$
2919    /// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed
2920    ///   to be 0.
2921    /// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2922    ///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is the maximum precision of the inputs.
2923    ///
2924    /// See the [`Float::agm`] documentation for information on special cases, overflow, and
2925    /// underflow.
2926    ///
2927    /// If you want to use a rounding mode other than `Nearest`, consider using
2928    /// [`Float::agm_prec_assign_ref`] instead. If you want to specify the output precision,
2929    /// consider using [`Float::agm_round_assign_ref`]. If you want both of these things, consider
2930    /// using [`Float::agm_prec_round_assign_ref`].
2931    ///
2932    /// # Worst-case complexity
2933    /// $T(n) = O(n (\log n)^2 \log\log n)$
2934    ///
2935    /// $M(n) = O(m)$
2936    ///
2937    /// where $T$ is time, $M$ is additional memory, $n$ is `max(self.significant_bits(),
2938    /// other.significant_bits())`, and $m$ is `other.significant_bits()`.
2939    ///
2940    /// # Examples
2941    /// ```
2942    /// use malachite_base::num::arithmetic::traits::AgmAssign;
2943    /// use malachite_float::Float;
2944    ///
2945    /// let mut x = Float::from_unsigned_prec(24u8, 100).0;
2946    /// x.agm_assign(&Float::from(6));
2947    /// assert_eq!(x.to_string(), "13.458171481725615420766813156976");
2948    /// ```
2949    #[inline]
2950    fn agm_assign(&mut self, other: &Self) {
2951        let prec = max(self.significant_bits(), other.significant_bits());
2952        self.agm_prec_round_assign_ref(other, prec, Nearest);
2953    }
2954}
2955
2956/// Computes the arithmetic-geometric mean (AGM) of two primitive floats.
2957///
2958/// $$
2959/// f(x,y) = \text{AGM}(x,y)+\varepsilon
2960/// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
2961/// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
2962/// $$
2963/// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
2964///   be 0.
2965/// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
2966///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is precision of the output (typically 24 if `T` is a
2967///   [`f32`] and 53 if `T` is a [`f64`], but less if the output is subnormal).
2968///
2969/// Special cases:
2970/// - $f(\text{NaN},x)=f(x,\text{NaN})=f(-\infty,x)=f(x,-\infty)=\text{NaN}$
2971/// - $f(\infty,x)=f(x,\infty)=\text{NaN}$ if $x\neq\infty$
2972/// - $f(\infty,\infty)=\infty$
2973/// - $f(\pm0.0,x)=f(x,\pm0.0)=0.0$
2974/// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
2975///
2976/// # Worst-case complexity
2977/// Constant time and additional memory.
2978///
2979/// # Examples
2980/// ```
2981/// use malachite_base::num::float::NiceFloat;
2982/// use malachite_float::float::arithmetic::agm::primitive_float_agm;
2983///
2984/// assert_eq!(
2985///     NiceFloat(primitive_float_agm(24.0, 6.0)),
2986///     NiceFloat(13.458171481725616)
2987/// );
2988/// ```
2989#[allow(clippy::type_repetition_in_bounds)]
2990#[inline]
2991pub fn primitive_float_agm<T: PrimitiveFloat>(x: T, y: T) -> T
2992where
2993    Float: From<T> + PartialOrd<T>,
2994    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
2995{
2996    emulate_float_float_to_float_fn(Float::agm_prec, x, y)
2997}
2998
2999/// Computes the arithmetic-geometric mean (AGM) of two [`Rational`]s, returning the result as a
3000/// primitive float.
3001///
3002/// $$
3003/// f(x,y) = \text{AGM}(x,y)+\varepsilon
3004/// =\frac{\pi}{2}\left(\int_0^{\frac{\pi}{2}}\frac{\mathrm{d}\theta}
3005/// {\sqrt{x^2\cos^2\theta+y^2\sin^2\theta}}\right)^{-1}+\varepsilon.
3006/// $$
3007/// - If $\text{AGM}(x,y)$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
3008///   be 0.
3009/// - If $\text{AGM}(x,y)$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2
3010///   \text{AGM}(x,y)\rfloor-p}$, where $p$ is precision of the output (typically 24 if `T` is a
3011///   [`f32`] and 53 if `T` is a [`f64`], but less if the output is subnormal).
3012///
3013/// Special cases:
3014/// - $f(0,x)=f(x,0)=0.0$
3015/// - $f(x,y)=\text{NaN}$ if $x<0$ or $y<0$
3016///
3017/// # Worst-case complexity
3018/// Constant time and additional memory.
3019///
3020/// # Examples
3021/// ```
3022/// use malachite_base::num::float::NiceFloat;
3023/// use malachite_float::float::arithmetic::agm::primitive_float_agm_rational;
3024/// use malachite_q::Rational;
3025///
3026/// assert_eq!(
3027///     NiceFloat(primitive_float_agm_rational::<f64>(
3028///         &Rational::from_unsigneds(2u8, 3),
3029///         &Rational::from_unsigneds(1u8, 5)
3030///     )),
3031///     NiceFloat(0.3985113702200345)
3032/// );
3033/// ```
3034#[allow(clippy::type_repetition_in_bounds)]
3035#[inline]
3036pub fn primitive_float_agm_rational<T: PrimitiveFloat>(x: &Rational, y: &Rational) -> T
3037where
3038    Float: PartialOrd<T>,
3039    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
3040{
3041    emulate_rational_rational_to_float_fn(Float::agm_rational_prec_ref_ref, x, y)
3042}