Skip to main content

malachite_float/float/arithmetic/
exp.rs

1// Copyright © 2026 Mikhail Hogrefe
2//
3// Uses code adopted from the GNU MPFR Library.
4//
5//      Copyright © 1999-2025 Free Software Foundation, Inc.
6//
7//      Contributed by the Pascaline 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
15// Port of MPFR's exponential. `mpfr_exp` (`exp.c`) is a dispatcher; the medium-precision workhorse
16// `mpfr_exp_2` (`exp_2.c`) uses Brent's method -- reduce x = n*log(2) + 2^K*r, sum the Taylor
17// series for the small r, raise to the 2^K power by K squarings, then scale by 2^n -- with the
18// series summed in fixed point. That fixed point is represented here as a malachite `Integer`
19// mantissa paired with an `i64` 2-exponent (MPFR's `mpz_t` + `mpfr_exp_t`).
20//
21// The Paterson-Stockmeyer series (exp2_aux2) and the high-precision exp_3 are not yet ported.
22
23use crate::InnerFloat::{Finite, Infinity, NaN, Zero};
24use crate::WIDTH_MINUS_1;
25use crate::{Float, emulate_float_to_float_fn, emulate_rational_to_float_fn, floor_and_ceiling};
26use alloc::vec;
27use core::cmp::Ordering::{self, Equal, Greater, Less};
28use core::cmp::max;
29use core::mem::swap;
30use malachite_base::fail_on_untested_path;
31use malachite_base::num::arithmetic::traits::{
32    CeilingLogBase2, Exp, ExpAssign, FloorRoot, FloorSqrt, IsPowerOf2, NegAssign, Parity, PowerOf2,
33    ShrRoundAssign, Sign, Square, SquareAssign, WrappingAddAssign,
34};
35use malachite_base::num::basic::floats::PrimitiveFloat;
36use malachite_base::num::basic::integers::PrimitiveInt;
37use malachite_base::num::basic::traits::{
38    Infinity as InfinityTrait, NaN as NaNTrait, One, Zero as ZeroTrait,
39};
40use malachite_base::num::conversion::traits::{ExactFrom, RoundingFrom, WrappingFrom};
41use malachite_base::num::logic::traits::SignificantBits;
42use malachite_base::rounding_modes::RoundingMode::{
43    self, Ceiling, Down, Exact, Floor, Nearest, Up,
44};
45use malachite_nz::integer::Integer;
46use malachite_nz::natural::Natural;
47use malachite_nz::natural::arithmetic::float_extras::float_can_round;
48use malachite_nz::platform::{Limb, SignedLimb};
49use malachite_q::Rational;
50
51// If the number of bits `k` of `z` exceeds `q`, divides `z` by `2 ^ (k - q)` (flooring) and returns
52// `k - q`; otherwise leaves `z` unchanged and returns 0.
53//
54// This is `mpz_normalize` from `exp_2.c`, MPFR 4.2.2.
55fn mpz_normalize(z: Integer, q: i64) -> (Integer, i64) {
56    let k = z.significant_bits();
57    if q < 0 || k > u64::exact_from(q) {
58        let shift = i64::exact_from(k) - q;
59        (z >> shift, shift)
60    } else {
61        // Currently unreachable from the naive series (`exp2_aux` always grows `t`/`rr` past `q`
62        // bits before truncating, and the squaring loop doubles past `q`); exercised once the
63        // Paterson-Stockmeyer path (`exp2_aux2`) is ported.
64        (z, 0)
65    }
66}
67
68// Shifts `z` so that its 2-exponent becomes `target`: right (flooring) by `target - expz` if
69// `target > expz`, otherwise left by `expz - target`. Returns `target`.
70//
71// This is `mpz_normalize2` from `exp_2.c`, MPFR 4.2.2. (A negative shift count reverses direction,
72// so the single `>>` covers both of MPFR's branches.)
73fn mpz_normalize2(z: Integer, expz: i64, target: i64) -> (Integer, i64) {
74    (z >> (target - expz), target)
75}
76
77// Returns the integer mantissa `m` and 2-exponent `e` of a finite nonzero `x`, so that `x = m *
78// 2^e` (the sign is carried by `m`). For a Malachite `Float`, `m` is the significand as a signed
79// integer and `e = exponent - significand_bits` (verified against 1.0: significand 2^63, exponent
80// 1, giving 2^63 * 2^(1-64) = 1).
81//
82// This is equivalent to `mpfr_get_z_2exp` from MPFR 4.2.2.
83fn get_z_2exp(x: Float) -> (Integer, i64) {
84    if let Finite {
85        sign,
86        exponent,
87        significand,
88        ..
89    } = x.0
90    {
91        let bits = significand.significant_bits();
92        let m = Integer::from_sign_and_abs(sign, significand);
93        (m, i64::from(exponent) - i64::exact_from(bits))
94    } else {
95        unreachable!()
96    }
97}
98
99// Computes `s = 1 + r/1! + r^2/2! + ... + r^l/l!` (continuing while the term is still significant
100// at precision `q`) in fixed point, where the returned `Integer` `s` and 2-exponent `exps` satisfy
101// (sum) = s * 2^exps. `r` must be pure FP (here it is positive and tiny). The naive method, O(l)
102// multiplications; the absolute error on the sum is less than `3*l*(l+1)*2^(-q)`, and that
103// `3*l*(l+1)` bound is the returned value. (`l` stays small for the precisions `exp_2` handles, so
104// the bound fits in a `u64`.)
105//
106// This is `mpfr_exp2_aux` from `exp_2.c`, MPFR 4.2.2.
107fn exp2_aux(r: Float, q: u64) -> (Integer, i64, u64) {
108    let qi = i64::exact_from(q);
109    let mut expt: i64 = 0;
110    let exps: i64 = 1 - qi; // s = 2^(q-1), i.e. the value 1
111    let mut t = Integer::ONE;
112    let mut s = Integer::power_of_2(q - 1);
113    let (mut rr, mut expr) = get_z_2exp(r); // rr * 2^expr = r, no error
114    let mut l: u64 = 0;
115    loop {
116        l += 1;
117        t *= &rr;
118        expt += expr;
119        let sbit = i64::exact_from(s.significant_bits());
120        let tbit = i64::exact_from(t.significant_bits());
121        let dif = exps + sbit - expt - tbit;
122        // truncate the bits of t that are below ulp(s) = 2^(1-q); error at most 2^(1-q)
123        let (t2, sh) = mpz_normalize(t, qi - dif);
124        t = t2;
125        expt += sh;
126        if l > 1 {
127            // divide by l to build r^l/l! (t >= 0, so truncation equals MPFR's floored division)
128            if l.is_power_of_2() {
129                // GMP doesn't optimize the power-of-2 case
130                t >>= l.ceiling_log_base_2();
131            } else {
132                t /= Integer::from(l);
133            }
134            debug_assert_eq!(expt, exps);
135        }
136        if t == 0 {
137            break;
138        }
139        s += &t; // exact
140        // keep rr the same size as t: the error on rr stays at most ulp(t) = ulp(s)
141        let tbit = i64::exact_from(t.significant_bits());
142        let (rr2, sh) = mpz_normalize(rr, tbit);
143        rr = rr2;
144        expr += sh;
145    }
146    (s, exps, 3 * l * (l + 1))
147}
148
149// Precision (in bits) at which `exp_2` switches from the naive `exp2_aux` (square-root `K`) to the
150// Paterson-Stockmeyer `exp2_aux2` (cube-root `K`). MPFR tunes `MPFR_EXP_2_THRESHOLD` per platform;
151// this is the generic default (`generic/mparam.h`), pending Malachite tuning.
152const EXP_2_THRESHOLD: u64 = 100;
153
154// Computes `s = 1 + r/1! + r^2/2! + ... + r^l/l!` (continuing while r^l/l! is still significant at
155// precision `q`) in fixed point, where the returned `Integer` `s` and 2-exponent `exps` satisfy
156// (sum) = s * 2^exps. `r` must be pure FP with exponent < 0 (here it is positive and tiny). Uses
157// the Paterson-Stockmeyer scheme: about `m + l/m` full multiplications (`2*sqrt(l)` for `m =
158// sqrt(l)`), versus `exp2_aux`'s O(l). The error is bounded by `l^2 + 4*l` ulps, and that `l*(l+4)`
159// bound is the returned value.
160//
161// This is `mpfr_exp2_aux2` from `exp_2.c`, MPFR 4.2.2.
162fn exp2_aux2(r: Float, q: u64) -> (Integer, i64, u64) {
163    let qi = i64::exact_from(q);
164    let one_minus_q = 1 - qi;
165    // estimate the value of l, then m ~ sqrt(l); we access R[2], so we need m >= 2
166    let expr0 = i64::from(r.get_exponent().unwrap());
167    debug_assert!(expr0 < 0);
168    let l_est = q / u64::exact_from(-expr0);
169    let m = max(2, usize::exact_from(l_est.floor_sqrt()));
170    // r_pows[i] = r^i (integer mantissa), exp_r_pows[i] its 2-exponent
171    let mut r_pows = vec![Integer::ZERO; m + 1];
172    let mut exp_r_pows = vec![0i64; m + 1];
173    let exps = one_minus_q; // 1 ulp = 2^(1-q)
174    let mut s = Integer::ZERO;
175    let (r1, e1) = get_z_2exp(r); // exact: no error
176    // normalize R[1] to exponent 1 - q (error <= 1 ulp)
177    let r1 = mpz_normalize2(r1, e1, one_minus_q).0;
178    r_pows[1] = r1;
179    exp_r_pows[1] = one_minus_q;
180    // R[2] = R[1]^2 >> (q - 1) (err <= 3 ulps)
181    let qm1 = q - 1;
182    r_pows[2] = (&r_pows[1]).square() >> qm1;
183    exp_r_pows[2] = one_minus_q;
184    for i in 3..=m {
185        // err(R[i]) <= 2*i-1 ulps
186        let t = if i.odd() {
187            &r_pows[i - 1] * &r_pows[1]
188        } else {
189            (&r_pows[i >> 1]).square()
190        };
191        r_pows[i] = t >> qm1;
192        exp_r_pows[i] = one_minus_q;
193    }
194    r_pows[0] = Integer::power_of_2(q - 1); // R[0] = 1
195    exp_r_pows[0] = one_minus_q;
196    let mut rr = Integer::ONE;
197    let mut expr: i64 = 0; // rr contains r^l/l!; by induction err(rr) <= 2*l ulps
198    let mut l: u64 = 0;
199    let mut ql = q; // precision used for the current giant step
200    loop {
201        let one_minus_ql = 1 - i64::exact_from(ql);
202        // all R[i] (i < m) must have exponent 1 - ql
203        if l != 0 {
204            for (r_pow, exp_r_pow) in r_pows[..m].iter_mut().zip(exp_r_pows[..m].iter_mut()) {
205                let z = core::mem::replace(r_pow, Integer::ZERO);
206                (*r_pow, *exp_r_pow) = mpz_normalize2(z, *exp_r_pow, one_minus_ql);
207            }
208        }
209        // t = R[m-1] normalized to exponent 1 - ql (err(t) <= 2*m-1 ulps)
210        let (mut t, mut expt) =
211            mpz_normalize2(r_pows[m - 1].clone(), exp_r_pows[m - 1], one_minus_ql);
212        // t = 1 + r/(l+1) + ... + r^(m-1)*l!/(l+m-1)! via Horner's scheme
213        for i in (0..m - 1).rev() {
214            t /= Integer::from(l + i as u64 + 1); // err(t) += 1 ulp
215            t += &r_pows[i];
216        }
217        // multiply t by r^l/l! and add to s
218        t *= &rr;
219        expt += expr;
220        let (t, et) = mpz_normalize2(t, expt, exps);
221        debug_assert_eq!(et, exps);
222        s += &t; // no error here
223        // update rr to r^(l+m)/(l+m)!
224        let mut t = &rr * &r_pows[m]; // err(t) <= err(rr) + 2m-1
225        expr += exp_r_pows[m];
226        let mut tmp = Integer::ONE;
227        for i in 1..=m {
228            tmp *= Integer::from(l + i as u64);
229        }
230        t /= tmp; // err(t) <= err(rr) + 2m
231        l += m as u64;
232        if t == 0 {
233            break;
234        }
235        let (rr2, sh) = mpz_normalize(t, i64::exact_from(ql));
236        rr = rr2;
237        expr += sh;
238        // in late giant steps `ql` can go <= 0 (s has grown past the working precision), so
239        // normalizing t to ql bits can shift it away entirely; rr is then 0.
240        let rrbit = if rr == 0 {
241            1
242        } else {
243            i64::exact_from(rr.significant_bits())
244        };
245        let sbit = i64::exact_from(s.significant_bits());
246        ql = (qi - exps - sbit + expr + rrbit) as u64;
247        // MPFR's own `(size_t)` cast here is admittedly dubious (see its TODO), but the operands
248        // cluster near -q, far from the wrap, so the unsigned and signed comparisons agree.
249        if (expr as u64).wrapping_add(rrbit as u64) <= q.wrapping_neg() {
250            break;
251        }
252    }
253    (s, exps, l * (l + 4))
254}
255
256// Precision (in bits) at or above which `exp` uses the binary-splitting `exp_3` (O(M(n) log(n)^2))
257// instead of `exp_2`. MPFR's generic `MPFR_EXP_THRESHOLD` default (`generic/mparam.h`), untuned.
258const EXP_THRESHOLD: u64 = 25000;
259
260// Extracts the `i`-th binary-splitting chunk of the mantissa of `p`, where `0 <= |p| < 1`, carrying
261// `p`'s sign. With `B = 2 ^ Limb::WIDTH`: chunk 0 is `floor(|p| * B)` (the top limb), and for `i >
262// 0`, chunk `i` is `(|p| * B^(2^i)) mod B^(2^(i-1))` -- the window of `2^(i-1)` limbs ending
263// `2^(i-1)` limbs below where chunk `i - 1` ends.
264//
265// This is `mpfr_extract` from `extract.c`, MPFR 4.2.2.
266fn extract(p: &Float, i: u64) -> Integer {
267    if let Finite {
268        sign, significand, ..
269    } = &p.0
270    {
271        let limbs = significand.as_limbs_asc();
272        let size_p = limbs.len();
273        let two_i = usize::power_of_2(i);
274        let two_i_2 = if i == 0 { 1 } else { two_i >> 1 };
275        let mut y = vec![0 as Limb; two_i_2];
276        if size_p < two_i {
277            // The window extends past the bottom of the mantissa: zero-fill and copy what's there.
278            if size_p >= two_i_2 {
279                let count = size_p - two_i_2;
280                y[two_i - size_p..][..count].copy_from_slice(&limbs[..count]);
281            } else {
282                // The whole window is below the mantissa (chunk all zero). Unreachable from
283                // `exp_3`: it only extracts chunks `i <= prec_x`, and `size_p > 2^(prec_x - 1) >=
284                // two_i_2`.
285                fail_on_untested_path("extract, window entirely below the mantissa");
286            }
287        } else {
288            y.copy_from_slice(&limbs[size_p - two_i..][..two_i_2]);
289        }
290        Integer::from_sign_and_abs(*sign, Natural::from_owned_limbs_asc(y))
291    } else {
292        unreachable!()
293    }
294}
295
296// Computes `y ~ exp(p / 2^r)` to precision `prec`, within 1 ulp, for `|p / 2^r| < 1`, using up to
297// `2^m` terms of the Taylor series summed by binary splitting. With `P(a,b) = p` if `a+1=b` else
298// `P(a,c)*P(c,b)`, `Q(a,b) = a*2^r` if `a+1=b` (except `Q(0,1)=1`) else `Q(a,c)*Q(c,b)`, and
299// `T(a,b) = P(a,b)` if `a+1=b` else `Q(c,b)*T(a,c) + P(a,c)*T(c,b)`, one has `exp(p/2^r) ~
300// T(0,i)/Q(0,i)`. Since `P(a,b) = p^(b-a)` and only `b-a = 2^j` occur, only the powers `p^(2^j)`
301// (the `ptoj` array) are precomputed; and since `Q(a,b)` is divisible by `2^(r*(b-a-1))`, that
302// power of two is tracked separately rather than stored.
303//
304// This is `mpfr_exp_rational` from `exp3.c`, MPFR 4.2.2.
305fn exp_rational(p: Integer, mut r: i64, m: usize, prec: u64) -> Float {
306    // Normalize p (strip trailing zeros); since |p/2^r| < 1 and p != 0, r stays >= 1.
307    let nz = p.trailing_zeros().unwrap();
308    let p = p >> nz;
309    r -= i64::exact_from(nz);
310    let scratch_len = m + 1;
311    let mut scratch = vec![Integer::ZERO; 3 * scratch_len];
312    split_into_chunks_mut!(scratch, scratch_len, [q, s], ptoj); // ptoj[k] = p^(2^k)
313    let mut scratch = vec![0u64; scratch_len << 1];
314    // P[k]/Q[k] for the remaining terms is <= 2^(-mult[k])
315    let (mult, log2_nb_terms) = scratch.split_at_mut(scratch_len);
316    ptoj[0] = p;
317    for k in 1..m {
318        ptoj[k] = (&ptoj[k - 1]).square();
319    }
320    q[0] = Integer::ONE;
321    s[0] = Integer::ONE;
322    let mut k = 0usize;
323    let mut prec_i_have: u64 = 0;
324    // Main loop: Q[0]*Q[1]*...*Q[k] equals i! as an invariant.
325    let n_terms = u64::power_of_2(u64::exact_from(m));
326    let mut i = 1u64;
327    while prec_i_have < prec && i < n_terms {
328        k += 1;
329        log2_nb_terms[k] = 0; // 1 term
330        q[k] = Integer::from(i + 1);
331        s[k] = Integer::from(i + 1);
332        let mut j = i + 1; // terms computed so far
333        let mut l = 0u32;
334        while j.even() {
335            // Combine and reduce: S[k] covers 2^l consecutive terms.
336            s[k] *= &ptoj[l as usize];
337            let mut t = &s[k - 1] * &q[k];
338            // Q[k] lacks the 2^(r*2^l) factor, so multiply it in when merging.
339            t <<= r << l;
340            t += &s[k];
341            s[k - 1] = t;
342            let (q_lo, q_hi) = q.split_at_mut(k);
343            *q_lo.last_mut().unwrap() *= &q_hi[0];
344            log2_nb_terms[k - 1] += 1;
345            prec_i_have = q[k].significant_bits();
346            let prec_ptoj = ptoj[l as usize].significant_bits();
347            mult[k - 1].wrapping_add_assign(
348                prec_i_have
349                    .wrapping_add(u64::wrapping_from(r << l))
350                    .wrapping_sub(prec_ptoj)
351                    .wrapping_sub(1),
352            );
353            prec_i_have = mult[k - 1];
354            mult[k] = mult[k - 1];
355            l += 1;
356            j >>= 1;
357            k -= 1;
358        }
359        i += 1;
360    }
361    // Accumulate all products into S[0] and Q[0].
362    let mut h = 0u64; // accumulated terms in the right part S[k]/Q[k]
363    while k > 0 {
364        let jj = log2_nb_terms[k - 1] as usize;
365        s[k] *= &ptoj[jj];
366        let mut t = &s[k - 1] * &q[k];
367        h += u64::power_of_2(log2_nb_terms[k]);
368        t <<= r * i64::exact_from(h);
369        t += &s[k];
370        s[k - 1] = t;
371        let (q_lo, q_hi) = q.split_at_mut(k);
372        *q_lo.last_mut().unwrap() *= &q_hi[0];
373        k -= 1;
374    }
375    // Q[0] now equals i!. Scale S[0] to ~2*prec bits and Q[0] to ~prec bits, then divide.
376    let mut s0 = core::mem::replace(&mut s[0], Integer::ZERO);
377    let mut q0 = core::mem::replace(&mut q[0], Integer::ZERO);
378    let mut diff = i64::exact_from(s0.significant_bits()) - (i64::exact_from(prec) << 1);
379    let mut expo = diff;
380    s0 >>= diff; // negative shift is a left shift, covering MPFR's mul_2exp branch
381    diff = i64::exact_from(q0.significant_bits()) - i64::exact_from(prec);
382    expo -= diff;
383    q0 >>= diff;
384    s0 /= q0; // truncating division (both positive)
385    // y = (S[0] rounded to prec) * 2^(expo - r*(i-1)); MPFR sets the mantissa via set_z then
386    // overrides the exponent, which is exactly this scaling. A direct `from_integer_prec_round(s0,
387    // ..)` would pass through the intermediate exponent sb(s0) ~ 2 * prec, which exceeds
388    // MAX_EXPONENT once prec approaches it (malachite's precision range exceeds its exponent range,
389    // unlike MPFR's, whose emax dwarfs any practical precision) and would silently saturate at the
390    // largest finite value. Attaching the scaling before the conversion keeps the exponent in
391    // range: the scaled value is a factor of exp(chunk), of ordinary size.
392    Float::from_rational_prec_round(
393        Rational::from(s0) << (expo - r * (i64::exact_from(i) - 1)),
394        prec,
395        Floor,
396    )
397    .0
398}
399
400// Computes `exp(x)` rounded to precision `precy` with rounding mode `rm`. Decomposes `x` into
401// limb-window chunks (`extract`), exponentiates each chunk's contribution with binary splitting
402// (`exp_rational`), and multiplies them, using O(M(n) log(n)^2) for high precision.
403//
404// This is `mpfr_exp_3` from `exp3.c`, MPFR 4.2.2.
405pub(crate) fn exp_3(x: &Float, precy: u64, rm: RoundingMode) -> (Float, Ordering) {
406    const SHIFT: u64 = Limb::WIDTH >> 1;
407    // prec_x: number of chunk levels, ~log2 of x's limb count.
408    let prec_x = x
409        .get_prec()
410        .unwrap()
411        .ceiling_log_base_2()
412        .saturating_sub(Limb::LOG_WIDTH);
413    let mut ttt = i64::from(x.get_exponent().unwrap());
414    let mut x_copy = x.clone();
415    let shift_x = if ttt > 0 {
416        // Shift x down to magnitude < 1.
417        let s = u64::exact_from(ttt);
418        x_copy = x >> s;
419        ttt = i64::from(x_copy.get_exponent().unwrap());
420        s
421    } else {
422        0
423    };
424    debug_assert!(ttt <= 0);
425    let mut realprec = precy + (prec_x + precy).ceiling_log_base_2();
426    let mut prec = realprec + SHIFT + 2 + shift_x;
427    let mut increment = Limb::WIDTH;
428    loop {
429        let k = prec.ceiling_log_base_2().saturating_sub(Limb::LOG_WIDTH);
430        let mut twopoweri = Limb::WIDTH;
431        // Particular case i = 0.
432        let uk = extract(&x_copy, 0);
433        debug_assert_ne!(uk, 0);
434        let mut tmp = exp_rational(
435            uk,
436            i64::exact_from(SHIFT + twopoweri) - ttt,
437            usize::exact_from(k + 1),
438            prec,
439        );
440        for _ in 0..SHIFT {
441            tmp.square_prec_round_assign(prec, Floor);
442        }
443        twopoweri <<= 1;
444        // General case.
445        let iter = k.min(prec_x);
446        for i in 1..=iter {
447            let uk = extract(&x_copy, i);
448            if uk != 0 {
449                let t = exp_rational(
450                    uk,
451                    i64::exact_from(twopoweri) - ttt,
452                    usize::exact_from(k - i + 1),
453                    prec,
454                );
455                tmp.mul_prec_round_assign(t, prec, Floor);
456            }
457            twopoweri <<= 1;
458        }
459        // Raise tmp to 2^shift_x to undo the initial down-shift of x; detect over/underflow.
460        let (val, scaled) = if shift_x > 0 {
461            for _ in 0..shift_x - 1 {
462                tmp.square_prec_round_assign(prec, Floor);
463            }
464            let mut t = tmp.square_prec_round_ref(prec, Floor).0;
465            if t.is_infinite() {
466                // Unreachable: `normal_ref` decides the overflow boundary exactly, so here exp(x) <
467                // 2^emax, every Floor-rounded intermediate lies below its true value, and no
468                // squaring can overflow. (Even if one somehow did, Floor rounding saturates at the
469                // largest finite value rather than reaching infinity.)
470                fail_on_untested_path("exp_3, overflow above normal_ref's bound_emax");
471                return exp_overflow(precy, rm);
472            }
473            let mut scaled = false;
474            if matches!(t.0, Zero { .. }) {
475                // Possibly spurious underflow: rescale by 2 and retry. Reachable only for x in the
476                // narrow band just above `normal_ref`'s `bound_emin`; exp's own test inputs never
477                // land there, but `Float::pow`'s do (its Ziv loop feeds y * ln|x| here at boundary
478                // magnitudes), and pow's property tests validate this path against MPFR.
479                tmp <<= 1;
480                t = tmp.square_prec_round_ref(prec, Floor).0;
481                if matches!(t.0, Zero { .. }) {
482                    // exact result < 2^(emin - 2): genuine underflow.
483                    return exp_underflow(precy, if rm == Nearest { Down } else { rm });
484                }
485                scaled = true;
486            }
487            (t, scaled)
488        } else {
489            (tmp, false)
490        };
491        if float_can_round(val.significand_ref().unwrap(), realprec, precy, rm) {
492            let mut y = val;
493            let mut inexact = y.set_prec_round(precy, rm);
494            if scaled && y.is_normal() {
495                // Undo the *2 scaling: y /= 4.
496                let ey = i64::from(y.get_exponent().unwrap());
497                let inex2 = y.shr_round_assign(2, rm);
498                if inex2 != Equal {
499                    // Underflow while unscaling.
500                    if rm == Nearest
501                        && inexact == Less
502                        && matches!(y.0, Zero { .. })
503                        && ey == i64::from(Float::MIN_EXPONENT) + 1
504                    {
505                        // Double rounding: RNDN rounded the scaled result down to 2^emin, but the
506                        // exact result is > 2^(emin - 2), so round up instead.
507                        (y, inexact) = (Float::min_positive_value_prec(precy), Greater);
508                    } else {
509                        inexact = inex2;
510                    }
511                }
512            }
513            return (y, inexact);
514        }
515        realprec += increment;
516        increment = realprec >> 1;
517        prec = realprec + SHIFT + 2 + shift_x;
518    }
519}
520
521// Computes `exp(x)` rounded to precision `precy` with rounding mode `rm`, returning the rounded
522// value and an [`Ordering`] comparing it to the exact result. `x` must be finite and nonzero and
523// `exp(x)` must be in range; the dispatcher (`exp`) guarantees both. Uses Brent's method: `exp(x) =
524// (1 + r + r^2/2! + ...)^(2^K) * 2^n` with `x = n*log(2) + 2^K*r`.
525//
526// Below `EXP_2_THRESHOLD` the naive series (`exp2_aux`) is used with the square-root `K`; at or
527// above it the Paterson-Stockmeyer series (`exp2_aux2`) is used with the cube-root `K`.
528//
529// This is `mpfr_exp_2` from `exp_2.c`, MPFR 4.2.2.
530pub(crate) fn exp_2(x: &Float, precy: u64, rm: RoundingMode) -> (Float, Ordering) {
531    let expx = i64::from(x.get_exponent().unwrap());
532    // Argument reduction: n ~ round(x / log(2)) (need not be exact).
533    let mut n: i64 = if expx <= -2 {
534        // |x| <= 0.25, so n = 0
535        0
536    } else {
537        let log2_est = Float::ln_2_prec_round(WIDTH_MINUS_1, Down).0;
538        let r_est = x.div_prec_ref_val(log2_est, WIDTH_MINUS_1).0;
539        i64::rounding_from(r_est, Nearest).0
540    };
541    // error_r bounds the bits cancelled in x - n*log(2)
542    let error_r: u64 = if n == 0 {
543        0
544    } else {
545        (n.unsigned_abs() + 1).significant_bits()
546    };
547    // Working-precision setup. Square-root K for the naive series, cube-root K for
548    // Paterson-Stockmeyer.
549    let k_param = if precy < EXP_2_THRESHOLD {
550        precy.div_ceil(2).floor_sqrt() + 3
551    } else {
552        (precy << 2).floor_root(3)
553    };
554    let l = (precy - 1) / k_param + 1;
555    let mut err = k_param + ((l << 1) + 18).ceiling_log_base_2();
556    let mut q = precy + err + k_param + 10;
557    // if |x| >> 1, account for the cancelled bits
558    if expx > 0 {
559        q += u64::exact_from(expx);
560    }
561    let mut increment = Limb::WIDTH;
562    loop {
563        let working = q + error_r;
564        // s is within 1 ulp of log(2), rounded so that r = x - n*log(2) is bounded above.
565        let s = Float::ln_2_prec_round(working, if n >= 0 { Down } else { Up }).0;
566        // r = |n| * log(2) (directed); negate when n < 0, so r <= n*log(2) within 3 ulps.
567        let mut r = s
568            .mul_prec_round_ref_val(
569                Float::from(n.unsigned_abs()),
570                working,
571                if n >= 0 { Down } else { Up },
572            )
573            .0;
574        if n < 0 {
575            r.neg_assign();
576        }
577        r = x.sub_prec_round_ref_val(r, working, Up).0;
578        // if the initial n was too large, r came out negative: reduce n
579        while r.is_normal() && r.is_sign_negative() {
580            n -= 1;
581            r.add_prec_round_assign_ref(&s, working, Up);
582        }
583        // if r is 0 we cannot round correctly; otherwise sum the series
584        if r.is_normal() {
585            // the cancelled low error_r bits of r are non-significant, so drop them
586            if error_r > 0 {
587                r.set_prec_round(q, Up);
588            }
589            // r = (x - n*log(2)) / 2^K, exact
590            r >>= k_param;
591            // ss <- 1 + r + r^2/2! + ... (naive method below the threshold, Paterson-Stockmeyer at
592            // or above it)
593            let (mut ss, mut exps, l_err) = if precy < EXP_2_THRESHOLD {
594                exp2_aux(r, q)
595            } else {
596                exp2_aux2(r, q)
597            };
598            // raise to the 2^K power by K squarings
599            for _ in 0..k_param {
600                ss.square_assign();
601                exps <<= 1;
602                let (ss2, sh) = mpz_normalize(ss, i64::exact_from(q));
603                ss = ss2;
604                exps += sh;
605            }
606            // s = ss * 2^exps (exact: ss has at most q bits and working >= q)
607            let s = Float::from_integer_prec(ss, working).0 << exps;
608            // error is at most 2^K * l_err, plus 2 for the 3-ulp error on r
609            err = k_param + l_err.ceiling_log_base_2() + 2;
610            if float_can_round(s.significand_ref().unwrap(), q - err, precy, rm) {
611                // y = s * 2^n, rounded to precy. `float_can_round` only returns true when s's
612                // trusted bits below precy are not all equal, i.e. s is not exactly representable
613                // at precy; since `shl_prec_round` rounds those same bits, it cannot come out Equal
614                // here. (This matches MPFR, which rounds and breaks with no special case -- exp of
615                // a finite nonzero value is irrational, never exactly representable.)
616                return s.shl_prec_round(n, precy, rm);
617            }
618        }
619        // If `r` is not normal it is 0: the rounded x - n*log(2) cancelled exactly, which happens
620        // iff x equals the working-precision rounding of n*log(2). The series can't be summed (it
621        // needs `r != 0`), so fall through to raise `q`; the higher-precision log(2) no longer
622        // rounds to x, so `r != 0` next time. This is MPFR's `MPFR_IS_ZERO(r)` case.
623        q += increment;
624        increment = q >> 1;
625    }
626}
627
628// The overflow result of exp (the value, which is positive, exceeds the maximum finite Float).
629//
630// This is `mpfr_overflow` (with positive sign) as used by `mpfr_exp`, MPFR 4.2.2.
631pub(crate) fn exp_overflow(precy: u64, rm: RoundingMode) -> (Float, Ordering) {
632    match rm {
633        Nearest | Up | Ceiling => (Float::INFINITY, Greater),
634        Down | Floor => (Float::max_finite_value_with_prec(precy), Less),
635        Exact => panic!("exp: Exact rounding was requested, but the result overflows"),
636    }
637}
638
639// The underflow result of exp (the value, which is positive, is below the minimum positive Float).
640// MPFR maps Nearest to toward-zero here, so Nearest joins Down/Floor.
641//
642// This is `mpfr_underflow` (with positive sign) as used by `mpfr_exp`, MPFR 4.2.2.
643pub(crate) fn exp_underflow(precy: u64, rm: RoundingMode) -> (Float, Ordering) {
644    match rm {
645        Nearest | Down | Floor => (Float::ZERO, Less),
646        Up | Ceiling => (Float::min_positive_value_prec(precy), Greater),
647        Exact => panic!("exp: Exact rounding was requested, but the result underflows"),
648    }
649}
650
651// Computes `exp(x)` for finite nonzero `x`, rounded to precision `precy` with rounding mode `rm`.
652// Detects overflow/underflow against `log(2)`-scaled exponent bounds, takes a fast path for tiny
653// `x` (where `exp(x) = 1 +/- ulp(1)`), and otherwise dispatches to `exp_2` (below `EXP_THRESHOLD`)
654// or the binary-splitting `exp_3` (at or above it).
655//
656// This is the finite-nonzero branch of `mpfr_exp` from `exp.c`, MPFR 4.2.2.
657fn exp_prec_round_normal_ref(x: &Float, precy: u64, rm: RoundingMode) -> (Float, Ordering) {
658    // exp of a finite nonzero value is transcendental, hence never exactly representable.
659    assert_ne!(rm, Exact, "Inexact exp");
660    // Overflow/underflow bounds, as ~64-bit Floats. Directed rounding makes `bound_emax` an upper
661    // bound on emax*log(2) and `bound_emin` a lower bound on (emin - 2)*log(2), so the comparisons
662    // below are sound one-sided tests.
663    const BP: u64 = 64;
664    const MAX_EXPONENT_FLOAT: Float = Float::const_from_signed(Float::MAX_EXPONENT as SignedLimb);
665    let (log2_lo, log2_hi) = floor_and_ceiling(Float::ln_2_prec_round(BP, Floor));
666    let bound_emax = log2_hi.mul_prec_round_ref_val(MAX_EXPONENT_FLOAT, BP, Up).0;
667    if *x >= bound_emax {
668        // x > log(2^emax), so exp(x) > 2^emax
669        return exp_overflow(precy, rm);
670    }
671    // `bound_emax` is an upper bound with ~2^-33 of slack, so an x just below it may still
672    // overflow. That sliver must be decided here: below the threshold, every intermediate in
673    // `exp_2` and `exp_3` stays under 2^emax, but a true overflow inside `exp_3` would saturate its
674    // Floor-rounded final squarings at the largest finite value instead of reaching infinity, and
675    // the saturated all-ones significand is one that `float_can_round` never certifies -- the Ziv
676    // loop would grow forever. Decide the sliver exactly, by comparing x with brackets of emax *
677    // log(2) as exact Rationals at widening precision; x is dyadic and the threshold is irrational,
678    // so the comparison always resolves. This mirrors the role of MPFR's overflow flag, which lets
679    // mpfr_exp detect the overflow after the fact.
680    let bound_emax_lo = log2_lo
681        .mul_prec_round_ref_val(MAX_EXPONENT_FLOAT, BP, Floor)
682        .0;
683    if *x >= bound_emax_lo {
684        let xr = Rational::exact_from(x);
685        let emax_r = Rational::from(Float::MAX_EXPONENT);
686        let mut p = 128;
687        loop {
688            let lo = Rational::exact_from(Float::ln_2_prec_round(p, Floor).0) * &emax_r;
689            if xr < lo {
690                break;
691            }
692            let hi = Rational::exact_from(Float::ln_2_prec_round(p, Ceiling).0) * &emax_r;
693            if xr >= hi {
694                // x > emax * log(2), so exp(x) > 2^emax
695                return exp_overflow(precy, rm);
696            }
697            p <<= 1;
698        }
699    }
700    let bound_emin = log2_hi
701        .mul_prec_round(
702            const { Float::const_from_signed((Float::MIN_EXPONENT as SignedLimb) - 2) },
703            BP,
704            Floor,
705        )
706        .0;
707    if *x <= bound_emin {
708        // x < log(2^(emin - 2)), so exp(x) < 2^(emin - 2)
709        return exp_underflow(precy, rm);
710    }
711    let expx = i64::from(x.get_exponent().unwrap());
712    // tiny x: if x < 2^(-precy), then exp(x) = 1 +/- ulp(1)
713    if expx < 0 && u64::exact_from(-expx) > precy {
714        return if x.is_sign_negative() && (rm == Down || rm == Floor) {
715            (one_neighbor(precy, false), Less) // 1 - ulp
716        } else if x.is_sign_positive() && (rm == Up || rm == Ceiling) {
717            (one_neighbor(precy, true), Greater) // 1 + ulp
718        } else {
719            (
720                Float::one_prec(precy),
721                if x.is_sign_positive() { Less } else { Greater },
722            )
723        };
724    }
725    if precy >= EXP_THRESHOLD {
726        exp_3(x, precy, rm)
727    } else {
728        exp_2(x, precy, rm)
729    }
730}
731
732// The neighbor of 1 at precision `prec`: the successor `1 + 2 ^ (1 - prec)` if `above`, otherwise
733// the predecessor `1 - 2 ^ (-prec)`. Both are exactly representable at precision `prec`. (Note that
734// `Float::increment`/`decrement` cannot be used here: they keep the ulp of the current binade, so
735// they bump the precision when crossing into the next binade and overshoot the true predecessor.
736// Also note that the significand cannot be built as a `Natural` and shifted into place: the
737// unshifted intermediate has exponent `prec`, which overflows to infinity when `prec` exceeds
738// `MAX_EXPONENT`, even though the final value's exponent is 0 or 1. Going through a `Rational`
739// keeps every intermediate exponent small. The `i64` conversion fails only for `prec >= 2^63`,
740// where a `Float` of that precision could not be materialized at all.)
741pub(crate) fn one_neighbor(prec: u64, above: bool) -> Float {
742    let p = i64::exact_from(prec);
743    Float::from_rational_prec_round(
744        if above {
745            Rational::ONE + Rational::power_of_2(1 - p)
746        } else {
747            Rational::ONE - Rational::power_of_2(-p)
748        },
749        prec,
750        Exact,
751    )
752    .0
753}
754
755// Computes `exp(x)` for a nonzero `Rational` `x` with `|x| < 1`, by summing its Taylor series
756// `exp(x) = sum x^k / k!`. Used when `x` is too small to be represented as a normal `Float` (so the
757// squeeze in `exp_rational_helper` cannot bracket it), in which case `exp(x)` is very close to 1
758// but may still be more than one ulp away from 1 when `prec` is enormous. The series is summed term
759// by term, bracketing the exact value between two rationals (consecutive partial sums for `x < 0`,
760// a partial sum and a remainder bound for `x > 0`) until both ends round to the same `Float`.
761// Working entirely with values near 1, this avoids ever representing `x` itself as a `Float`.
762pub(crate) fn exp_rational_near_one(
763    x: &Rational,
764    prec: u64,
765    rm: RoundingMode,
766) -> (Float, Ordering) {
767    let negative = x.sign() == Less;
768    let mut s = Rational::ONE; // partial sum S_{k-1}
769    let mut term = Rational::ONE; // x^(k-1) / (k-1)!
770    let mut k = 1u64;
771    loop {
772        term *= x;
773        term /= Rational::from(k); // term = x^k / k!
774        let s_next = &s + &term; // S_k
775        let (lo, hi) = if negative {
776            // The terms alternate in sign with strictly decreasing magnitude (|x| / (k + 1) < 1),
777            // so exp(x) lies between consecutive partial sums.
778            if s < s_next {
779                (s.clone(), s_next.clone())
780            } else {
781                (s_next.clone(), s.clone())
782            }
783        } else {
784            // Every term is positive, so S_k < exp(x), and the remainder is bounded by t_{k+1} / (1
785            // - x).
786            let next = (&term * x) / Rational::from(k + 1); // t_{k+1}
787            (s_next.clone(), &s_next + next / (Rational::ONE - x))
788        };
789        s = s_next;
790        k += 1;
791        let (f_lo, mut o_lo) = Float::from_rational_prec_round_ref(&lo, prec, rm);
792        let (f_hi, mut o_hi) = Float::from_rational_prec_round_ref(&hi, prec, rm);
793        // A bound that is exactly representable at `prec` rounds with `Equal`; treat it as agreeing
794        // with the other bound. (`hi == 1` triggers this for small negative x, since 1 is exact;
795        // the `lo` case only arises when a partial sum lands exactly on a `prec`-bit Float, which
796        // needs an enormous `prec`.)
797        if o_lo == Equal {
798            o_lo = o_hi;
799        }
800        if o_hi == Equal {
801            o_hi = o_lo;
802        }
803        if o_lo == o_hi && f_lo == f_hi {
804            return (f_lo, o_lo);
805        }
806    }
807}
808
809// Computes `exp(x)` for a nonzero `Rational` `x`, rounded to precision `prec` with rounding mode
810// `rm`. (`exp(0) = 1` is handled by the caller.) Because the exponential of a nonzero rational is
811// transcendental, the result is never exactly representable, so `rm` must not be `Exact`.
812fn exp_rational_helper(x: &Rational, prec: u64, rm: RoundingMode) -> (Float, Ordering) {
813    assert_ne!(rm, Exact, "Inexact exp");
814    let positive = x.sign() == Greater;
815    let exp_x = x.floor_log_base_2_abs() + 1; // the MPFR-style exponent of x
816    // x is too small to be represented as a normal Float (|x| < 2^MIN_EXPONENT). The squeeze below
817    // cannot bracket it (its Float bounds would be 0 or out of range), so sum the Taylor series
818    // instead. exp(x) is near 1 but, for an enormous `prec`, possibly more than one ulp away.
819    if exp_x <= Float::MIN_EXPONENT_I64 {
820        return exp_rational_near_one(x, prec, rm);
821    }
822    // Tiny x: if |x| < 2^(-prec-1) then exp(x) is within half an ulp of 1, so it rounds to 1 (or,
823    // for directed rounding away from 1, to the neighbor of 1). This mirrors exp's tiny-x fast
824    // path.
825    if -exp_x > i64::exact_from(prec) {
826        return match (positive, rm) {
827            (false, Down | Floor) => (one_neighbor(prec, false), Less), // 1 - ulp
828            (true, Up | Ceiling) => (one_neighbor(prec, true), Greater), // 1 + ulp
829            (true, _) => (Float::one_prec(prec), Less),
830            (false, _) => (Float::one_prec(prec), Greater),
831        };
832    }
833    // |x| is too large to be a finite Float, so exp(x) overflows (x > 0) or underflows (x < 0).
834    // Smaller x that still overflow/underflow exp are caught by `exp_prec_round_normal_ref` in the
835    // loop below.
836    if exp_x >= Float::MAX_EXPONENT_I64 {
837        return if positive {
838            exp_overflow(prec, rm)
839        } else {
840            exp_underflow(prec, rm)
841        };
842    }
843    // General case: bracket x between the Floats x_lo <= x <= x_hi, exponentiate both, and increase
844    // the working precision until the two bounds round to the same result. exp is monotonic, so
845    // once the bounds agree the exact exp(x) (which lies between them) rounds the same way.
846    let mut working_prec = prec + 10;
847    let mut increment = Limb::WIDTH;
848    loop {
849        let (x_lo, x_o) = Float::from_rational_prec_round_ref(x, working_prec, Floor);
850        if x_o == Equal {
851            // x is exactly representable at `working_prec`, so exp(x) is simply exp(x_lo).
852            return exp_prec_round_normal_ref(&x_lo, prec, rm);
853        }
854        let (x_lo, x_hi) = floor_and_ceiling((x_lo, x_o));
855        // exp of a finite nonzero Float is transcendental, so `exp_prec_round_normal_ref` is never
856        // exact: both orderings are `Less` or `Greater`, never `Equal`.
857        let (e_lo, o_lo) = exp_prec_round_normal_ref(&x_lo, prec, rm);
858        let (e_hi, o_hi) = exp_prec_round_normal_ref(&x_hi, prec, rm);
859        if o_lo == o_hi && e_lo == e_hi {
860            return (e_lo, o_lo);
861        }
862        working_prec += increment;
863        increment = working_prec >> 1;
864    }
865}
866
867impl Float {
868    /// Computes $e^x$, the exponential of a [`Float`], rounding the result to the specified
869    /// precision and with the specified rounding mode. The [`Float`] is taken by value. An
870    /// [`Ordering`] is also returned, indicating whether the rounded exponential is less than,
871    /// equal to, or greater than the exact exponential. Although `NaN`s are not comparable to any
872    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
873    ///
874    /// See [`RoundingMode`] for a description of the possible rounding modes.
875    ///
876    /// $$
877    /// f(x,p,m) = e^x+\varepsilon.
878    /// $$
879    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
880    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
881    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$.
882    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
883    ///   2^{\lfloor\log_2 e^x\rfloor-p}$.
884    ///
885    /// If the output has a precision, it is `prec`.
886    ///
887    /// Special cases:
888    /// - $f(\text{NaN},p,m)=\text{NaN}$
889    /// - $f(\infty,p,m)=\infty$
890    /// - $f(-\infty,p,m)=0.0$
891    /// - $f(\pm0.0,p,m)=1.0$
892    ///
893    /// Overflow and underflow:
894    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
895    ///   returned instead.
896    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$ is
897    ///   returned instead.
898    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
899    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned instead.
900    /// - If $f(x,p,m)\leq2^{-2^{30}-1}$ and $m$ is `Nearest`, $0.0$ is returned instead.
901    /// - If $2^{-2^{30}-1}<f(x,p,m)<2^{-2^{30}}$ and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
902    ///   instead.
903    ///
904    /// If you know you'll be using `Nearest`, consider using [`Float::exp_prec`] instead. If you
905    /// know that your target precision is the precision of the input, consider using
906    /// [`Float::exp_round`] instead. If both of these things are true, consider using
907    /// [`Float::exp`] instead.
908    ///
909    /// # Worst-case complexity
910    /// $T(n) = O(n^{3/2} \log n \log\log n)$
911    ///
912    /// $M(n) = O(n \log n)$
913    ///
914    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
915    ///
916    /// # Panics
917    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the given
918    /// precision.
919    ///
920    /// # Examples
921    /// ```
922    /// use malachite_base::rounding_modes::RoundingMode::*;
923    /// use malachite_float::Float;
924    /// use std::cmp::Ordering::*;
925    ///
926    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
927    ///     .0
928    ///     .exp_prec_round(5, Floor);
929    /// assert_eq!(e.to_string(), "2.62");
930    /// assert_eq!(o, Less);
931    ///
932    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
933    ///     .0
934    ///     .exp_prec_round(5, Ceiling);
935    /// assert_eq!(e.to_string(), "2.75");
936    /// assert_eq!(o, Greater);
937    ///
938    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
939    ///     .0
940    ///     .exp_prec_round(5, Nearest);
941    /// assert_eq!(e.to_string(), "2.75");
942    /// assert_eq!(o, Greater);
943    ///
944    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
945    ///     .0
946    ///     .exp_prec_round(20, Floor);
947    /// assert_eq!(e.to_string(), "2.7182808");
948    /// assert_eq!(o, Less);
949    ///
950    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
951    ///     .0
952    ///     .exp_prec_round(20, Ceiling);
953    /// assert_eq!(e.to_string(), "2.7182846");
954    /// assert_eq!(o, Greater);
955    ///
956    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
957    ///     .0
958    ///     .exp_prec_round(20, Nearest);
959    /// assert_eq!(e.to_string(), "2.7182808");
960    /// assert_eq!(o, Less);
961    /// ```
962    #[inline]
963    pub fn exp_prec_round(self, prec: u64, rm: RoundingMode) -> (Self, Ordering) {
964        self.exp_prec_round_ref(prec, rm)
965    }
966
967    /// Computes $e^x$, the exponential of a [`Float`], rounding the result to the specified
968    /// precision and with the specified rounding mode. The [`Float`] is taken by reference. An
969    /// [`Ordering`] is also returned, indicating whether the rounded exponential is less than,
970    /// equal to, or greater than the exact exponential. Although `NaN`s are not comparable to any
971    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
972    ///
973    /// See [`RoundingMode`] for a description of the possible rounding modes.
974    ///
975    /// $$
976    /// f(x,p,m) = e^x+\varepsilon.
977    /// $$
978    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
979    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
980    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$.
981    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
982    ///   2^{\lfloor\log_2 e^x\rfloor-p}$.
983    ///
984    /// If the output has a precision, it is `prec`.
985    ///
986    /// Special cases:
987    /// - $f(\text{NaN},p,m)=\text{NaN}$
988    /// - $f(\infty,p,m)=\infty$
989    /// - $f(-\infty,p,m)=0.0$
990    /// - $f(\pm0.0,p,m)=1.0$
991    ///
992    /// Overflow and underflow:
993    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
994    ///   returned instead.
995    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$ is
996    ///   returned instead.
997    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
998    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned instead.
999    /// - If $f(x,p,m)\leq2^{-2^{30}-1}$ and $m$ is `Nearest`, $0.0$ is returned instead.
1000    /// - If $2^{-2^{30}-1}<f(x,p,m)<2^{-2^{30}}$ and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
1001    ///   instead.
1002    ///
1003    /// If you know you'll be using `Nearest`, consider using [`Float::exp_prec_ref`] instead. If
1004    /// you know that your target precision is the precision of the input, consider using
1005    /// [`Float::exp_round_ref`] instead. If both of these things are true, consider using
1006    /// `(&Float).exp()` instead.
1007    ///
1008    /// # Worst-case complexity
1009    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1010    ///
1011    /// $M(n) = O(n \log n)$
1012    ///
1013    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1014    ///
1015    /// # Panics
1016    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the given
1017    /// precision.
1018    ///
1019    /// # Examples
1020    /// ```
1021    /// use malachite_base::rounding_modes::RoundingMode::*;
1022    /// use malachite_float::Float;
1023    /// use std::cmp::Ordering::*;
1024    ///
1025    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1026    ///     .0
1027    ///     .exp_prec_round_ref(5, Floor);
1028    /// assert_eq!(e.to_string(), "2.62");
1029    /// assert_eq!(o, Less);
1030    ///
1031    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1032    ///     .0
1033    ///     .exp_prec_round_ref(5, Ceiling);
1034    /// assert_eq!(e.to_string(), "2.75");
1035    /// assert_eq!(o, Greater);
1036    ///
1037    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1038    ///     .0
1039    ///     .exp_prec_round_ref(5, Nearest);
1040    /// assert_eq!(e.to_string(), "2.75");
1041    /// assert_eq!(o, Greater);
1042    ///
1043    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1044    ///     .0
1045    ///     .exp_prec_round_ref(20, Floor);
1046    /// assert_eq!(e.to_string(), "2.7182808");
1047    /// assert_eq!(o, Less);
1048    ///
1049    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1050    ///     .0
1051    ///     .exp_prec_round_ref(20, Ceiling);
1052    /// assert_eq!(e.to_string(), "2.7182846");
1053    /// assert_eq!(o, Greater);
1054    ///
1055    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1056    ///     .0
1057    ///     .exp_prec_round_ref(20, Nearest);
1058    /// assert_eq!(e.to_string(), "2.7182808");
1059    /// assert_eq!(o, Less);
1060    /// ```
1061    pub fn exp_prec_round_ref(&self, prec: u64, rm: RoundingMode) -> (Self, Ordering) {
1062        assert_ne!(prec, 0);
1063        match &self.0 {
1064            NaN => (Self::NAN, Equal),
1065            // exp(+inf) = +inf; exp(-inf) = +0
1066            Infinity { sign } => {
1067                if *sign {
1068                    (Self::INFINITY, Equal)
1069                } else {
1070                    (Self::ZERO, Equal)
1071                }
1072            }
1073            // exp(+0) = exp(-0) = 1
1074            Zero { .. } => (Self::one_prec(prec), Equal),
1075            Finite { .. } => exp_prec_round_normal_ref(self, prec, rm),
1076        }
1077    }
1078
1079    /// Computes $e^x$, the exponential of a [`Float`], rounding the result to the nearest value of
1080    /// the specified precision. The [`Float`] is taken by value. An [`Ordering`] is also returned,
1081    /// indicating whether the rounded exponential is less than, equal to, or greater than the exact
1082    /// exponential. Although `NaN`s are not comparable to any [`Float`], whenever this function
1083    /// returns a `NaN` it also returns `Equal`.
1084    ///
1085    /// If the exponential is equidistant from two [`Float`]s with the specified precision, the
1086    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1087    /// description of the `Nearest` rounding mode.
1088    ///
1089    /// $$
1090    /// f(x,p) = e^x+\varepsilon.
1091    /// $$
1092    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1093    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$.
1094    ///
1095    /// If the output has a precision, it is `prec`.
1096    ///
1097    /// Special cases:
1098    /// - $f(\text{NaN},p)=\text{NaN}$
1099    /// - $f(\infty,p)=\infty$
1100    /// - $f(-\infty,p)=0.0$
1101    /// - $f(\pm0.0,p)=1.0$
1102    ///
1103    /// Overflow and underflow:
1104    /// - If $f(x,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
1105    /// - If $f(x,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
1106    /// - If $2^{-2^{30}-1}<f(x,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
1107    ///
1108    /// If you want to use a rounding mode other than `Nearest`, consider using
1109    /// [`Float::exp_prec_round`] instead. If you know that your target precision is the precision
1110    /// of the input, consider using [`Float::exp`] instead.
1111    ///
1112    /// # Worst-case complexity
1113    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1114    ///
1115    /// $M(n) = O(n \log n)$
1116    ///
1117    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1118    ///
1119    /// # Examples
1120    /// ```
1121    /// use malachite_float::Float;
1122    /// use std::cmp::Ordering::*;
1123    ///
1124    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_prec(5);
1125    /// assert_eq!(e.to_string(), "2.75");
1126    /// assert_eq!(o, Greater);
1127    ///
1128    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_prec(20);
1129    /// assert_eq!(e.to_string(), "2.7182808");
1130    /// assert_eq!(o, Less);
1131    /// ```
1132    #[inline]
1133    pub fn exp_prec(self, prec: u64) -> (Self, Ordering) {
1134        self.exp_prec_round(prec, Nearest)
1135    }
1136
1137    /// Computes $e^x$, the exponential of a [`Float`], rounding the result to the nearest value of
1138    /// the specified precision. The [`Float`] is taken by reference. An [`Ordering`] is also
1139    /// returned, indicating whether the rounded exponential is less than, equal to, or greater than
1140    /// the exact exponential. Although `NaN`s are not comparable to any [`Float`], whenever this
1141    /// function returns a `NaN` it also returns `Equal`.
1142    ///
1143    /// If the exponential is equidistant from two [`Float`]s with the specified precision, the
1144    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1145    /// description of the `Nearest` rounding mode.
1146    ///
1147    /// $$
1148    /// f(x,p) = e^x+\varepsilon.
1149    /// $$
1150    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1151    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$.
1152    ///
1153    /// If the output has a precision, it is `prec`.
1154    ///
1155    /// Special cases:
1156    /// - $f(\text{NaN},p)=\text{NaN}$
1157    /// - $f(\infty,p)=\infty$
1158    /// - $f(-\infty,p)=0.0$
1159    /// - $f(\pm0.0,p)=1.0$
1160    ///
1161    /// Overflow and underflow:
1162    /// - If $f(x,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
1163    /// - If $f(x,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
1164    /// - If $2^{-2^{30}-1}<f(x,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
1165    ///
1166    /// If you want to use a rounding mode other than `Nearest`, consider using
1167    /// [`Float::exp_prec_round_ref`] instead. If you know that your target precision is the
1168    /// precision of the input, consider using `(&Float).exp()` instead.
1169    ///
1170    /// # Worst-case complexity
1171    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1172    ///
1173    /// $M(n) = O(n \log n)$
1174    ///
1175    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1176    ///
1177    /// # Examples
1178    /// ```
1179    /// use malachite_float::Float;
1180    /// use std::cmp::Ordering::*;
1181    ///
1182    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_prec_ref(5);
1183    /// assert_eq!(e.to_string(), "2.75");
1184    /// assert_eq!(o, Greater);
1185    ///
1186    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_prec_ref(20);
1187    /// assert_eq!(e.to_string(), "2.7182808");
1188    /// assert_eq!(o, Less);
1189    /// ```
1190    #[inline]
1191    pub fn exp_prec_ref(&self, prec: u64) -> (Self, Ordering) {
1192        self.exp_prec_round_ref(prec, Nearest)
1193    }
1194
1195    /// Computes $e^x$, the exponential of a [`Float`], rounding the result with the specified
1196    /// rounding mode. The [`Float`] is taken by value. An [`Ordering`] is also returned, indicating
1197    /// whether the rounded exponential is less than, equal to, or greater than the exact
1198    /// exponential. Although `NaN`s are not comparable to any [`Float`], whenever this function
1199    /// returns a `NaN` it also returns `Equal`.
1200    ///
1201    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
1202    /// description of the possible rounding modes.
1203    ///
1204    /// $$
1205    /// f(x,m) = e^x+\varepsilon.
1206    /// $$
1207    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1208    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
1209    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$, where $p$ is the precision of the input.
1210    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1211    ///   2^{\lfloor\log_2 e^x\rfloor-p}$, where $p$ is the precision of the input.
1212    ///
1213    /// If the output has a precision, it is the precision of the input.
1214    ///
1215    /// Special cases:
1216    /// - $f(\text{NaN},m)=\text{NaN}$
1217    /// - $f(\infty,m)=\infty$
1218    /// - $f(-\infty,m)=0.0$
1219    /// - $f(\pm0.0,m)=1.0$
1220    ///
1221    /// See the [`Float::exp_prec_round`] documentation for information on overflow and underflow.
1222    ///
1223    /// If you want to specify an output precision, consider using [`Float::exp_prec_round`]
1224    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1225    /// [`Float::exp`] instead.
1226    ///
1227    /// # Worst-case complexity
1228    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1229    ///
1230    /// $M(n) = O(n \log n)$
1231    ///
1232    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1233    ///
1234    /// # Panics
1235    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the input
1236    /// precision.
1237    ///
1238    /// # Examples
1239    /// ```
1240    /// use malachite_base::rounding_modes::RoundingMode::*;
1241    /// use malachite_float::Float;
1242    /// use std::cmp::Ordering::*;
1243    ///
1244    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_round(Floor);
1245    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713512");
1246    /// assert_eq!(o, Less);
1247    ///
1248    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_round(Ceiling);
1249    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713544");
1250    /// assert_eq!(o, Greater);
1251    ///
1252    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_round(Nearest);
1253    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713512");
1254    /// assert_eq!(o, Less);
1255    /// ```
1256    #[inline]
1257    pub fn exp_round(self, rm: RoundingMode) -> (Self, Ordering) {
1258        let prec = self.significant_bits();
1259        self.exp_prec_round(prec, rm)
1260    }
1261
1262    /// Computes $e^x$, the exponential of a [`Float`], rounding the result with the specified
1263    /// rounding mode. The [`Float`] is taken by reference. An [`Ordering`] is also returned,
1264    /// indicating whether the rounded exponential is less than, equal to, or greater than the exact
1265    /// exponential. Although `NaN`s are not comparable to any [`Float`], whenever this function
1266    /// returns a `NaN` it also returns `Equal`.
1267    ///
1268    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
1269    /// description of the possible rounding modes.
1270    ///
1271    /// $$
1272    /// f(x,m) = e^x+\varepsilon.
1273    /// $$
1274    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1275    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
1276    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$, where $p$ is the precision of the input.
1277    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1278    ///   2^{\lfloor\log_2 e^x\rfloor-p}$, where $p$ is the precision of the input.
1279    ///
1280    /// If the output has a precision, it is the precision of the input.
1281    ///
1282    /// Special cases:
1283    /// - $f(\text{NaN},m)=\text{NaN}$
1284    /// - $f(\infty,m)=\infty$
1285    /// - $f(-\infty,m)=0.0$
1286    /// - $f(\pm0.0,m)=1.0$
1287    ///
1288    /// See the [`Float::exp_prec_round`] documentation for information on overflow and underflow.
1289    ///
1290    /// If you want to specify an output precision, consider using [`Float::exp_prec_round_ref`]
1291    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1292    /// `(&Float).exp()` instead.
1293    ///
1294    /// # Worst-case complexity
1295    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1296    ///
1297    /// $M(n) = O(n \log n)$
1298    ///
1299    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1300    ///
1301    /// # Panics
1302    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the input
1303    /// precision.
1304    ///
1305    /// # Examples
1306    /// ```
1307    /// use malachite_base::rounding_modes::RoundingMode::*;
1308    /// use malachite_float::Float;
1309    /// use std::cmp::Ordering::*;
1310    ///
1311    /// let (e, o) = Float::from_unsigned_prec(1u32, 100).0.exp_round_ref(Floor);
1312    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713512");
1313    /// assert_eq!(o, Less);
1314    ///
1315    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1316    ///     .0
1317    ///     .exp_round_ref(Ceiling);
1318    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713544");
1319    /// assert_eq!(o, Greater);
1320    ///
1321    /// let (e, o) = Float::from_unsigned_prec(1u32, 100)
1322    ///     .0
1323    ///     .exp_round_ref(Nearest);
1324    /// assert_eq!(e.to_string(), "2.7182818284590452353602874713512");
1325    /// assert_eq!(o, Less);
1326    /// ```
1327    #[inline]
1328    pub fn exp_round_ref(&self, rm: RoundingMode) -> (Self, Ordering) {
1329        let prec = self.significant_bits();
1330        self.exp_prec_round_ref(prec, rm)
1331    }
1332
1333    /// Computes $e^x$, the exponential of a [`Float`], in place, rounding the result to the
1334    /// specified precision and with the specified rounding mode. An [`Ordering`] is returned,
1335    /// indicating whether the rounded exponential is less than, equal to, or greater than the exact
1336    /// exponential. Although `NaN`s are not comparable to any [`Float`], whenever this function
1337    /// sets the [`Float`] to `NaN` it also returns `Equal`.
1338    ///
1339    /// See [`RoundingMode`] for a description of the possible rounding modes.
1340    ///
1341    /// $$
1342    /// x \gets e^x+\varepsilon.
1343    /// $$
1344    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1345    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
1346    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$.
1347    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1348    ///   2^{\lfloor\log_2 e^x\rfloor-p}$.
1349    ///
1350    /// If the output has a precision, it is `prec`.
1351    ///
1352    /// See the [`Float::exp_prec_round`] documentation for information on special cases, overflow,
1353    /// and underflow.
1354    ///
1355    /// If you know you'll be using `Nearest`, consider using [`Float::exp_prec_assign`] instead. If
1356    /// you know that your target precision is the precision of the input, consider using
1357    /// [`Float::exp_round_assign`] instead. If both of these things are true, consider using
1358    /// [`Float::exp_assign`] instead.
1359    ///
1360    /// # Worst-case complexity
1361    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1362    ///
1363    /// $M(n) = O(n \log n)$
1364    ///
1365    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1366    ///
1367    /// # Panics
1368    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the given
1369    /// precision.
1370    ///
1371    /// # Examples
1372    /// ```
1373    /// use malachite_base::rounding_modes::RoundingMode::*;
1374    /// use malachite_float::Float;
1375    /// use std::cmp::Ordering::*;
1376    ///
1377    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1378    /// assert_eq!(x.exp_prec_round_assign(5, Floor), Less);
1379    /// assert_eq!(x.to_string(), "2.62");
1380    ///
1381    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1382    /// assert_eq!(x.exp_prec_round_assign(5, Ceiling), Greater);
1383    /// assert_eq!(x.to_string(), "2.75");
1384    ///
1385    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1386    /// assert_eq!(x.exp_prec_round_assign(5, Nearest), Greater);
1387    /// assert_eq!(x.to_string(), "2.75");
1388    ///
1389    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1390    /// assert_eq!(x.exp_prec_round_assign(20, Floor), Less);
1391    /// assert_eq!(x.to_string(), "2.7182808");
1392    ///
1393    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1394    /// assert_eq!(x.exp_prec_round_assign(20, Ceiling), Greater);
1395    /// assert_eq!(x.to_string(), "2.7182846");
1396    ///
1397    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1398    /// assert_eq!(x.exp_prec_round_assign(20, Nearest), Less);
1399    /// assert_eq!(x.to_string(), "2.7182808");
1400    /// ```
1401    #[inline]
1402    pub fn exp_prec_round_assign(&mut self, prec: u64, rm: RoundingMode) -> Ordering {
1403        let mut x = Self::ZERO;
1404        swap(self, &mut x);
1405        let o;
1406        (*self, o) = x.exp_prec_round(prec, rm);
1407        o
1408    }
1409
1410    /// Computes $e^x$, the exponential of a [`Float`], in place, rounding the result to the nearest
1411    /// value of the specified precision. An [`Ordering`] is returned, indicating whether the
1412    /// rounded exponential is less than, equal to, or greater than the exact exponential. Although
1413    /// `NaN`s are not comparable to any [`Float`], whenever this function sets the [`Float`] to
1414    /// `NaN` it also returns `Equal`.
1415    ///
1416    /// If the exponential is equidistant from two [`Float`]s with the specified precision, the
1417    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1418    /// description of the `Nearest` rounding mode.
1419    ///
1420    /// $$
1421    /// x \gets e^x+\varepsilon.
1422    /// $$
1423    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1424    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$.
1425    ///
1426    /// If the output has a precision, it is `prec`.
1427    ///
1428    /// See the [`Float::exp_prec`] documentation for information on special cases, overflow, and
1429    /// underflow.
1430    ///
1431    /// If you want to use a rounding mode other than `Nearest`, consider using
1432    /// [`Float::exp_prec_round_assign`] instead. If you know that your target precision is the
1433    /// precision of the input, consider using [`Float::exp_assign`] instead.
1434    ///
1435    /// # Worst-case complexity
1436    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1437    ///
1438    /// $M(n) = O(n \log n)$
1439    ///
1440    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1441    ///
1442    /// # Examples
1443    /// ```
1444    /// use malachite_float::Float;
1445    /// use std::cmp::Ordering::*;
1446    ///
1447    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1448    /// assert_eq!(x.exp_prec_assign(5), Greater);
1449    /// assert_eq!(x.to_string(), "2.75");
1450    ///
1451    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1452    /// assert_eq!(x.exp_prec_assign(20), Less);
1453    /// assert_eq!(x.to_string(), "2.7182808");
1454    /// ```
1455    #[inline]
1456    pub fn exp_prec_assign(&mut self, prec: u64) -> Ordering {
1457        self.exp_prec_round_assign(prec, Nearest)
1458    }
1459
1460    /// Computes $e^x$, the exponential of a [`Float`], in place, rounding the result with the
1461    /// specified rounding mode. An [`Ordering`] is returned, indicating whether the rounded
1462    /// exponential is less than, equal to, or greater than the exact exponential. Although `NaN`s
1463    /// are not comparable to any [`Float`], whenever this function sets the [`Float`] to `NaN` it
1464    /// also returns `Equal`.
1465    ///
1466    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
1467    /// description of the possible rounding modes.
1468    ///
1469    /// $$
1470    /// x \gets e^x+\varepsilon.
1471    /// $$
1472    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1473    /// - If $e^x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
1474    ///   2^{\lfloor\log_2 e^x\rfloor-p+1}$, where $p$ is the precision of the input.
1475    /// - If $e^x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1476    ///   2^{\lfloor\log_2 e^x\rfloor-p}$, where $p$ is the precision of the input.
1477    ///
1478    /// If the output has a precision, it is the precision of the input.
1479    ///
1480    /// See the [`Float::exp_round`] documentation for information on special cases, overflow, and
1481    /// underflow.
1482    ///
1483    /// If you want to specify an output precision, consider using [`Float::exp_prec_round_assign`]
1484    /// instead. If you know you'll be using the `Nearest` rounding mode, consider using
1485    /// [`Float::exp_assign`] instead.
1486    ///
1487    /// # Worst-case complexity
1488    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1489    ///
1490    /// $M(n) = O(n \log n)$
1491    ///
1492    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1493    ///
1494    /// # Panics
1495    /// Panics if `rm` is `Exact` but the result cannot be represented exactly with the input
1496    /// precision.
1497    ///
1498    /// # Examples
1499    /// ```
1500    /// use malachite_base::rounding_modes::RoundingMode::*;
1501    /// use malachite_float::Float;
1502    /// use std::cmp::Ordering::*;
1503    ///
1504    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1505    /// assert_eq!(x.exp_round_assign(Floor), Less);
1506    /// assert_eq!(x.to_string(), "2.7182818284590452353602874713512");
1507    ///
1508    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1509    /// assert_eq!(x.exp_round_assign(Ceiling), Greater);
1510    /// assert_eq!(x.to_string(), "2.7182818284590452353602874713544");
1511    ///
1512    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1513    /// assert_eq!(x.exp_round_assign(Nearest), Less);
1514    /// assert_eq!(x.to_string(), "2.7182818284590452353602874713512");
1515    /// ```
1516    #[inline]
1517    pub fn exp_round_assign(&mut self, rm: RoundingMode) -> Ordering {
1518        let prec = self.significant_bits();
1519        self.exp_prec_round_assign(prec, rm)
1520    }
1521
1522    #[allow(clippy::needless_pass_by_value)]
1523    /// Computes $e^x$, the exponential of a [`Rational`], rounding the result to the specified
1524    /// precision and with the specified rounding mode and returning the result as a [`Float`]. The
1525    /// [`Rational`] is taken by value. An [`Ordering`] is also returned, indicating whether the
1526    /// rounded exponential is less than, equal to, or greater than the exact exponential.
1527    ///
1528    /// See [`RoundingMode`] for a description of the possible rounding modes.
1529    ///
1530    /// $$
1531    /// f(x,p,m) = e^x+\varepsilon.
1532    /// $$
1533    /// - If $m$ is not `Nearest`, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p+1}$.
1534    /// - If $m$ is `Nearest`, then $|\varepsilon| \leq 2^{\lfloor\log_2 e^x\rfloor-p}$.
1535    ///
1536    /// These bounds do not apply when the result overflows or underflows; see below.
1537    ///
1538    /// The output has precision `prec`.
1539    ///
1540    /// Special cases:
1541    /// - $f(0,p,m)=1$.
1542    ///
1543    /// Overflow and underflow:
1544    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
1545    ///   returned instead.
1546    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$ is
1547    ///   returned instead.
1548    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
1549    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned instead.
1550    /// - If $f(x,p,m)\leq2^{-2^{30}-1}$ and $m$ is `Nearest`, $0.0$ is returned instead.
1551    /// - If $2^{-2^{30}-1}<f(x,p,m)<2^{-2^{30}}$ and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
1552    ///   instead.
1553    ///
1554    /// If you know you'll be using `Nearest`, consider using [`Float::exp_rational_prec`] instead.
1555    ///
1556    /// # Worst-case complexity
1557    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1558    ///
1559    /// $M(n) = O(n \log n)$
1560    ///
1561    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1562    ///
1563    /// # Panics
1564    /// Panics if `prec` is zero, or if `rm` is `Exact` but the result cannot be represented exactly
1565    /// with the given precision (which is the case for every nonzero input).
1566    ///
1567    /// # Examples
1568    /// ```
1569    /// use malachite_base::rounding_modes::RoundingMode::*;
1570    /// use malachite_float::Float;
1571    /// use malachite_q::Rational;
1572    /// use std::cmp::Ordering::*;
1573    ///
1574    /// let (e, o) = Float::exp_rational_prec_round(Rational::from_unsigneds(3u8, 5), 5, Floor);
1575    /// assert_eq!(e.to_string(), "1.81");
1576    /// assert_eq!(o, Less);
1577    ///
1578    /// let (e, o) = Float::exp_rational_prec_round(Rational::from_unsigneds(3u8, 5), 5, Ceiling);
1579    /// assert_eq!(e.to_string(), "1.88");
1580    /// assert_eq!(o, Greater);
1581    ///
1582    /// let (e, o) = Float::exp_rational_prec_round(Rational::from_unsigneds(3u8, 5), 20, Floor);
1583    /// assert_eq!(e.to_string(), "1.8221188");
1584    /// assert_eq!(o, Less);
1585    ///
1586    /// let (e, o) = Float::exp_rational_prec_round(Rational::from_unsigneds(3u8, 5), 20, Ceiling);
1587    /// assert_eq!(e.to_string(), "1.8221207");
1588    /// assert_eq!(o, Greater);
1589    /// ```
1590    #[inline]
1591    pub fn exp_rational_prec_round(x: Rational, prec: u64, rm: RoundingMode) -> (Self, Ordering) {
1592        Self::exp_rational_prec_round_ref(&x, prec, rm)
1593    }
1594
1595    /// Computes $e^x$, the exponential of a [`Rational`], rounding the result to the specified
1596    /// precision and with the specified rounding mode and returning the result as a [`Float`]. The
1597    /// [`Rational`] is taken by reference. An [`Ordering`] is also returned, indicating whether the
1598    /// rounded exponential is less than, equal to, or greater than the exact exponential.
1599    ///
1600    /// See [`RoundingMode`] for a description of the possible rounding modes.
1601    ///
1602    /// $$
1603    /// f(x,p,m) = e^x+\varepsilon.
1604    /// $$
1605    /// - If $m$ is not `Nearest`, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p+1}$.
1606    /// - If $m$ is `Nearest`, then $|\varepsilon| \leq 2^{\lfloor\log_2 e^x\rfloor-p}$.
1607    ///
1608    /// These bounds do not apply when the result overflows or underflows; see below.
1609    ///
1610    /// The output has precision `prec`.
1611    ///
1612    /// Special cases:
1613    /// - $f(0,p,m)=1$.
1614    ///
1615    /// Overflow and underflow:
1616    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Ceiling`, `Up`, or `Nearest`, $\infty$ is
1617    ///   returned instead.
1618    /// - If $f(x,p,m)\geq 2^{2^{30}-1}$ and $m$ is `Floor` or `Down`, $(1-(1/2)^p)2^{2^{30}-1}$ is
1619    ///   returned instead.
1620    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Floor` or `Down`, $0.0$ is returned instead.
1621    /// - If $f(x,p,m)<2^{-2^{30}}$ and $m$ is `Ceiling` or `Up`, $2^{-2^{30}}$ is returned instead.
1622    /// - If $f(x,p,m)\leq2^{-2^{30}-1}$ and $m$ is `Nearest`, $0.0$ is returned instead.
1623    /// - If $2^{-2^{30}-1}<f(x,p,m)<2^{-2^{30}}$ and $m$ is `Nearest`, $2^{-2^{30}}$ is returned
1624    ///   instead.
1625    ///
1626    /// If you know you'll be using `Nearest`, consider using [`Float::exp_rational_prec_ref`]
1627    /// instead.
1628    ///
1629    /// # Worst-case complexity
1630    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1631    ///
1632    /// $M(n) = O(n \log n)$
1633    ///
1634    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1635    ///
1636    /// # Panics
1637    /// Panics if `prec` is zero, or if `rm` is `Exact` but the result cannot be represented exactly
1638    /// with the given precision (which is the case for every nonzero input).
1639    ///
1640    /// # Examples
1641    /// ```
1642    /// use malachite_base::rounding_modes::RoundingMode::*;
1643    /// use malachite_float::Float;
1644    /// use malachite_q::Rational;
1645    /// use std::cmp::Ordering::*;
1646    ///
1647    /// let (e, o) =
1648    ///     Float::exp_rational_prec_round_ref(&Rational::from_unsigneds(3u8, 5), 5, Floor);
1649    /// assert_eq!(e.to_string(), "1.81");
1650    /// assert_eq!(o, Less);
1651    ///
1652    /// let (e, o) =
1653    ///     Float::exp_rational_prec_round_ref(&Rational::from_unsigneds(3u8, 5), 5, Ceiling);
1654    /// assert_eq!(e.to_string(), "1.88");
1655    /// assert_eq!(o, Greater);
1656    ///
1657    /// let (e, o) =
1658    ///     Float::exp_rational_prec_round_ref(&Rational::from_unsigneds(3u8, 5), 20, Floor);
1659    /// assert_eq!(e.to_string(), "1.8221188");
1660    /// assert_eq!(o, Less);
1661    ///
1662    /// let (e, o) =
1663    ///     Float::exp_rational_prec_round_ref(&Rational::from_unsigneds(3u8, 5), 20, Ceiling);
1664    /// assert_eq!(e.to_string(), "1.8221207");
1665    /// assert_eq!(o, Greater);
1666    /// ```
1667    pub fn exp_rational_prec_round_ref(
1668        x: &Rational,
1669        prec: u64,
1670        rm: RoundingMode,
1671    ) -> (Self, Ordering) {
1672        assert_ne!(prec, 0);
1673        if *x == 0u32 {
1674            // exp(0) = 1, exactly.
1675            return (Self::one_prec(prec), Equal);
1676        }
1677        exp_rational_helper(x, prec, rm)
1678    }
1679
1680    #[allow(clippy::needless_pass_by_value)]
1681    /// Computes $e^x$, the exponential of a [`Rational`], rounding the result to the nearest value
1682    /// of the specified precision and returning the result as a [`Float`]. The [`Rational`] is
1683    /// taken by value. An [`Ordering`] is also returned, indicating whether the rounded exponential
1684    /// is less than, equal to, or greater than the exact exponential.
1685    ///
1686    /// If the exponential is equidistant from two [`Float`]s with the specified precision, the
1687    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1688    /// description of the `Nearest` rounding mode.
1689    ///
1690    /// $$
1691    /// f(x,p) = e^x+\varepsilon,
1692    /// $$
1693    /// where $|\varepsilon| \leq 2^{\lfloor\log_2 e^x\rfloor-p}$ (unless the result overflows or
1694    /// underflows; see below).
1695    ///
1696    /// The output has precision `prec`.
1697    ///
1698    /// Special cases:
1699    /// - $f(0,p)=1$.
1700    ///
1701    /// Overflow and underflow:
1702    /// - If $f(x,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
1703    /// - If $f(x,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
1704    /// - If $2^{-2^{30}-1}<f(x,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
1705    ///
1706    /// If you want to use a rounding mode other than `Nearest`, consider using
1707    /// [`Float::exp_rational_prec_round`] instead.
1708    ///
1709    /// # Worst-case complexity
1710    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1711    ///
1712    /// $M(n) = O(n \log n)$
1713    ///
1714    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1715    ///
1716    /// # Panics
1717    /// Panics if `prec` is zero.
1718    ///
1719    /// # Examples
1720    /// ```
1721    /// use malachite_float::Float;
1722    /// use malachite_q::Rational;
1723    /// use std::cmp::Ordering::*;
1724    ///
1725    /// let (e, o) = Float::exp_rational_prec(Rational::from_unsigneds(3u8, 5), 5);
1726    /// assert_eq!(e.to_string(), "1.81");
1727    /// assert_eq!(o, Less);
1728    ///
1729    /// let (e, o) = Float::exp_rational_prec(Rational::from_unsigneds(3u8, 5), 20);
1730    /// assert_eq!(e.to_string(), "1.8221188");
1731    /// assert_eq!(o, Less);
1732    ///
1733    /// let (e, o) = Float::exp_rational_prec(Rational::from(0), 10);
1734    /// assert_eq!(e.to_string(), "1.0000");
1735    /// assert_eq!(o, Equal);
1736    /// ```
1737    #[inline]
1738    pub fn exp_rational_prec(x: Rational, prec: u64) -> (Self, Ordering) {
1739        Self::exp_rational_prec_round_ref(&x, prec, Nearest)
1740    }
1741
1742    /// Computes $e^x$, the exponential of a [`Rational`], rounding the result to the nearest value
1743    /// of the specified precision and returning the result as a [`Float`]. The [`Rational`] is
1744    /// taken by reference. An [`Ordering`] is also returned, indicating whether the rounded
1745    /// exponential is less than, equal to, or greater than the exact exponential.
1746    ///
1747    /// If the exponential is equidistant from two [`Float`]s with the specified precision, the
1748    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1749    /// description of the `Nearest` rounding mode.
1750    ///
1751    /// $$
1752    /// f(x,p) = e^x+\varepsilon,
1753    /// $$
1754    /// where $|\varepsilon| \leq 2^{\lfloor\log_2 e^x\rfloor-p}$ (unless the result overflows or
1755    /// underflows; see below).
1756    ///
1757    /// The output has precision `prec`.
1758    ///
1759    /// Special cases:
1760    /// - $f(0,p)=1$.
1761    ///
1762    /// Overflow and underflow:
1763    /// - If $f(x,p)\geq 2^{2^{30}-1}$, $\infty$ is returned instead.
1764    /// - If $f(x,p)\leq2^{-2^{30}-1}$, $0.0$ is returned instead.
1765    /// - If $2^{-2^{30}-1}<f(x,p)<2^{-2^{30}}$, $2^{-2^{30}}$ is returned instead.
1766    ///
1767    /// If you want to use a rounding mode other than `Nearest`, consider using
1768    /// [`Float::exp_rational_prec_round_ref`] instead.
1769    ///
1770    /// # Worst-case complexity
1771    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1772    ///
1773    /// $M(n) = O(n \log n)$
1774    ///
1775    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1776    ///
1777    /// # Panics
1778    /// Panics if `prec` is zero.
1779    ///
1780    /// # Examples
1781    /// ```
1782    /// use malachite_float::Float;
1783    /// use malachite_q::Rational;
1784    /// use std::cmp::Ordering::*;
1785    ///
1786    /// let (e, o) = Float::exp_rational_prec_ref(&Rational::from_unsigneds(3u8, 5), 5);
1787    /// assert_eq!(e.to_string(), "1.81");
1788    /// assert_eq!(o, Less);
1789    ///
1790    /// let (e, o) = Float::exp_rational_prec_ref(&Rational::from_unsigneds(3u8, 5), 20);
1791    /// assert_eq!(e.to_string(), "1.8221188");
1792    /// assert_eq!(o, Less);
1793    ///
1794    /// let (e, o) = Float::exp_rational_prec_ref(&Rational::from(0), 10);
1795    /// assert_eq!(e.to_string(), "1.0000");
1796    /// assert_eq!(o, Equal);
1797    /// ```
1798    #[inline]
1799    pub fn exp_rational_prec_ref(x: &Rational, prec: u64) -> (Self, Ordering) {
1800        Self::exp_rational_prec_round_ref(x, prec, Nearest)
1801    }
1802}
1803
1804impl Exp for Float {
1805    type Output = Self;
1806
1807    /// Computes $e^x$, the exponential of a [`Float`], taking it by value.
1808    ///
1809    /// If the output has a precision, it is the precision of the input. If the exponential is
1810    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1811    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1812    /// rounding mode.
1813    ///
1814    /// $$
1815    /// f(x) = e^x+\varepsilon.
1816    /// $$
1817    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1818    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$,
1819    ///   where $p$ is the precision of the input.
1820    ///
1821    /// Special cases:
1822    /// - $f(\text{NaN})=\text{NaN}$
1823    /// - $f(\infty)=\infty$
1824    /// - $f(-\infty)=0.0$
1825    /// - $f(\pm0.0)=1.0$
1826    ///
1827    /// See the [`Float::exp_round`] documentation for information on overflow and underflow.
1828    ///
1829    /// If you want to use a rounding mode other than `Nearest`, consider using [`Float::exp_round`]
1830    /// instead. If you want to specify the output precision, consider using [`Float::exp_prec`]. If
1831    /// you want both of these things, consider using [`Float::exp_prec_round`].
1832    ///
1833    /// # Worst-case complexity
1834    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1835    ///
1836    /// $M(n) = O(n \log n)$
1837    ///
1838    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1839    ///
1840    /// # Examples
1841    /// ```
1842    /// use malachite_base::num::arithmetic::traits::Exp;
1843    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity, Zero};
1844    /// use malachite_float::Float;
1845    ///
1846    /// assert!(Float::NAN.exp().is_nan());
1847    /// assert_eq!(Float::INFINITY.exp(), Float::INFINITY);
1848    /// assert_eq!(Float::NEGATIVE_INFINITY.exp(), Float::ZERO);
1849    /// assert_eq!(
1850    ///     Float::from_unsigned_prec(1u32, 100).0.exp().to_string(),
1851    ///     "2.7182818284590452353602874713512"
1852    /// );
1853    /// ```
1854    #[inline]
1855    fn exp(self) -> Self {
1856        let prec = self.significant_bits();
1857        self.exp_prec_round(prec, Nearest).0
1858    }
1859}
1860
1861impl Exp for &Float {
1862    type Output = Float;
1863
1864    /// Computes $e^x$, the exponential of a [`Float`], taking it by reference.
1865    ///
1866    /// If the output has a precision, it is the precision of the input. If the exponential is
1867    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1868    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1869    /// rounding mode.
1870    ///
1871    /// $$
1872    /// f(x) = e^x+\varepsilon.
1873    /// $$
1874    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1875    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$,
1876    ///   where $p$ is the precision of the input.
1877    ///
1878    /// Special cases:
1879    /// - $f(\text{NaN})=\text{NaN}$
1880    /// - $f(\infty)=\infty$
1881    /// - $f(-\infty)=0.0$
1882    /// - $f(\pm0.0)=1.0$
1883    ///
1884    /// See the [`Float::exp_round`] documentation for information on overflow and underflow.
1885    ///
1886    /// If you want to use a rounding mode other than `Nearest`, consider using
1887    /// [`Float::exp_round_ref`] instead. If you want to specify the output precision, consider
1888    /// using [`Float::exp_prec_ref`]. If you want both of these things, consider using
1889    /// [`Float::exp_prec_round_ref`].
1890    ///
1891    /// # Worst-case complexity
1892    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1893    ///
1894    /// $M(n) = O(n \log n)$
1895    ///
1896    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1897    ///
1898    /// # Examples
1899    /// ```
1900    /// use malachite_base::num::arithmetic::traits::Exp;
1901    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity, Zero};
1902    /// use malachite_float::Float;
1903    ///
1904    /// assert!((&Float::NAN).exp().is_nan());
1905    /// assert_eq!((&Float::INFINITY).exp(), Float::INFINITY);
1906    /// assert_eq!((&Float::NEGATIVE_INFINITY).exp(), Float::ZERO);
1907    /// assert_eq!(
1908    ///     (&Float::from_unsigned_prec(1u32, 100).0).exp().to_string(),
1909    ///     "2.7182818284590452353602874713512"
1910    /// );
1911    /// ```
1912    #[inline]
1913    fn exp(self) -> Float {
1914        let prec = self.significant_bits();
1915        self.exp_prec_round_ref(prec, Nearest).0
1916    }
1917}
1918
1919impl ExpAssign for Float {
1920    /// Computes $e^x$, the exponential of a [`Float`], in place.
1921    ///
1922    /// If the output has a precision, it is the precision of the input. If the exponential is
1923    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1924    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1925    /// rounding mode.
1926    ///
1927    /// $$
1928    /// x \gets e^x+\varepsilon.
1929    /// $$
1930    /// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1931    /// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$,
1932    ///   where $p$ is the precision of the input.
1933    ///
1934    /// See the [`Float::exp`] documentation for information on special cases, overflow, and
1935    /// underflow.
1936    ///
1937    /// If you want to use a rounding mode other than `Nearest`, consider using
1938    /// [`Float::exp_round_assign`] instead. If you want to specify the output precision, consider
1939    /// using [`Float::exp_prec_assign`]. If you want both of these things, consider using
1940    /// [`Float::exp_prec_round_assign`].
1941    ///
1942    /// # Worst-case complexity
1943    /// $T(n) = O(n^{3/2} \log n \log\log n)$
1944    ///
1945    /// $M(n) = O(n \log n)$
1946    ///
1947    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.significant_bits()`.
1948    ///
1949    /// # Examples
1950    /// ```
1951    /// use malachite_base::num::arithmetic::traits::ExpAssign;
1952    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity, Zero};
1953    /// use malachite_float::Float;
1954    ///
1955    /// let mut x = Float::NAN;
1956    /// x.exp_assign();
1957    /// assert!(x.is_nan());
1958    ///
1959    /// let mut x = Float::INFINITY;
1960    /// x.exp_assign();
1961    /// assert_eq!(x, Float::INFINITY);
1962    ///
1963    /// let mut x = Float::NEGATIVE_INFINITY;
1964    /// x.exp_assign();
1965    /// assert_eq!(x, Float::ZERO);
1966    ///
1967    /// let mut x = Float::from_unsigned_prec(1u32, 100).0;
1968    /// x.exp_assign();
1969    /// assert_eq!(x.to_string(), "2.7182818284590452353602874713512");
1970    /// ```
1971    #[inline]
1972    fn exp_assign(&mut self) {
1973        let prec = self.significant_bits();
1974        self.exp_prec_round_assign(prec, Nearest);
1975    }
1976}
1977
1978/// Computes $e^x$, the exponential of a primitive float. Using this function is more accurate than
1979/// using the default `exp` function or the one provided by `libm`.
1980///
1981/// $$
1982/// f(x) = e^x+\varepsilon.
1983/// $$
1984/// - If $e^x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be 0.
1985/// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$, where
1986///   $p$ is the precision of the output (typically 24 if `T` is a [`f32`] and 53 if `T` is a
1987///   [`f64`], but less if the output is subnormal).
1988///
1989/// Special cases:
1990/// - $f(\text{NaN})=\text{NaN}$
1991/// - $f(\infty)=\infty$
1992/// - $f(-\infty)=0.0$
1993/// - $f(\pm0.0)=1.0$
1994///
1995/// Overflow and underflow are possible: a large positive `x` gives $\infty$, and a large negative
1996/// `x` gives `0.0`.
1997///
1998/// # Worst-case complexity
1999/// Constant time and additional memory.
2000///
2001/// # Examples
2002/// ```
2003/// use malachite_base::num::basic::traits::NegativeInfinity;
2004/// use malachite_base::num::float::NiceFloat;
2005/// use malachite_float::float::arithmetic::exp::primitive_float_exp;
2006///
2007/// assert!(primitive_float_exp(f32::NAN).is_nan());
2008/// assert_eq!(
2009///     NiceFloat(primitive_float_exp(f32::INFINITY)),
2010///     NiceFloat(f32::INFINITY)
2011/// );
2012/// assert_eq!(
2013///     NiceFloat(primitive_float_exp(f32::NEGATIVE_INFINITY)),
2014///     NiceFloat(0.0)
2015/// );
2016/// assert_eq!(NiceFloat(primitive_float_exp(0.0f32)), NiceFloat(1.0));
2017/// assert_eq!(NiceFloat(primitive_float_exp(1.0f32)), NiceFloat(2.7182817));
2018/// ```
2019#[inline]
2020#[allow(clippy::type_repetition_in_bounds)]
2021pub fn primitive_float_exp<T: PrimitiveFloat>(x: T) -> T
2022where
2023    Float: From<T> + PartialOrd<T>,
2024    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
2025{
2026    emulate_float_to_float_fn(Float::exp_prec, x)
2027}
2028
2029/// Computes $e^x$, the exponential of a [`Rational`], returning the result as a primitive float.
2030///
2031/// $$
2032/// f(x) = e^x+\varepsilon.
2033/// $$
2034/// - If $e^x$ is infinite or zero, $\varepsilon$ may be ignored or assumed to be 0.
2035/// - If $e^x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 e^x\rfloor-p}$, where
2036///   $p$ is the precision of the output (typically 24 if `T` is a [`f32`] and 53 if `T` is a
2037///   [`f64`], but less if the output is subnormal).
2038///
2039/// Special cases:
2040/// - $f(0)=1$
2041///
2042/// Overflow and underflow are possible: a large positive `x` gives $\infty$, and a large negative
2043/// `x` gives `0.0`.
2044///
2045/// # Worst-case complexity
2046/// Constant time and additional memory.
2047///
2048/// # Examples
2049/// ```
2050/// use malachite_base::num::basic::traits::Zero;
2051/// use malachite_base::num::float::NiceFloat;
2052/// use malachite_float::float::arithmetic::exp::primitive_float_exp_rational;
2053/// use malachite_q::Rational;
2054///
2055/// assert_eq!(
2056///     NiceFloat(primitive_float_exp_rational::<f64>(&Rational::ZERO)),
2057///     NiceFloat(1.0)
2058/// );
2059/// assert_eq!(
2060///     NiceFloat(primitive_float_exp_rational::<f64>(
2061///         &Rational::from_unsigneds(1u8, 3)
2062///     )),
2063///     NiceFloat(1.3956124250860895)
2064/// );
2065/// assert_eq!(
2066///     NiceFloat(primitive_float_exp_rational::<f64>(&Rational::from(10000))),
2067///     NiceFloat(f64::INFINITY)
2068/// );
2069/// assert_eq!(
2070///     NiceFloat(primitive_float_exp_rational::<f64>(&Rational::from(-10000))),
2071///     NiceFloat(0.0)
2072/// );
2073/// ```
2074#[inline]
2075#[allow(clippy::type_repetition_in_bounds)]
2076pub fn primitive_float_exp_rational<T: PrimitiveFloat>(x: &Rational) -> T
2077where
2078    Float: PartialOrd<T>,
2079    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
2080{
2081    emulate_rational_to_float_fn(Float::exp_rational_prec_ref, x)
2082}