Skip to main content

malachite_float/float/arithmetic/
log_base_power_of_2.rs

1// Copyright © 2026 Mikhail Hogrefe
2//
3// This file is part of Malachite.
4//
5// Malachite is free software: you can redistribute it and/or modify it under the terms of the GNU
6// Lesser General Public License (LGPL) as published by the Free Software Foundation; either version
7// 3 of the License, or (at your option) any later version. See <https://www.gnu.org/licenses/>.
8
9use crate::InnerFloat::{Finite, Infinity, NaN, Zero};
10use crate::float::arithmetic::ln::{SliverOfOne, sliver_of_one};
11use crate::float::arithmetic::log_base_2::extended_log_base_2_of_rational;
12use crate::float::basic::extended::ExtendedFloat;
13use crate::{
14    Float, emulate_float_to_float_fn, emulate_rational_to_float_fn, float_either_zero,
15    float_infinity, float_nan, float_negative_infinity,
16};
17use core::cmp::Ordering::{self, *};
18use malachite_base::num::arithmetic::traits::{
19    CeilingLogBase2, CheckedLogBase2, IsPowerOf2, LogBasePowerOf2, LogBasePowerOf2Assign, Sign,
20};
21use malachite_base::num::basic::floats::PrimitiveFloat;
22use malachite_base::num::basic::integers::PrimitiveInt;
23use malachite_base::num::basic::traits::Zero as ZeroTrait;
24use malachite_base::num::conversion::traits::{ExactFrom, RoundingFrom};
25use malachite_base::num::logic::traits::SignificantBits;
26use malachite_base::rounding_modes::RoundingMode::{self, *};
27use malachite_nz::natural::arithmetic::float_extras::float_can_round;
28use malachite_nz::platform::Limb;
29use malachite_q::Rational;
30
31// The computation of log_base_power_of_2(x, pow) is done by log_{2^pow}(x) = log_2(x) / pow, where
32// the input is finite, nonzero, and positive.
33fn log_base_power_of_2_prec_round_normal(
34    x: &Float,
35    pow: i64,
36    prec: u64,
37    rm: RoundingMode,
38) -> (Float, Ordering) {
39    // If x is 1, the result is 0.
40    if *x == 1u32 {
41        return (Float::ZERO, Equal);
42    }
43    // If x is 2^m, then log_2(x) = m and the result is the rational m / pow (exact when
44    // representable at the target precision).
45    if x.is_power_of_2() {
46        let m = i64::from(x.get_exponent().unwrap()) - 1;
47        return Float::from(m).div_prec_round(Float::from(pow), prec, rm);
48    }
49    // log_{2^pow}(x) for x in a sliver of 1 can fall below the smallest positive Float; the
50    // 1-plus-x form handles that underflow region.
51    match sliver_of_one(x) {
52        SliverOfOne::Representable(d) => {
53            return d.log_base_power_of_2_1_plus_x_prec_round(pow, prec, rm);
54        }
55        SliverOfOne::Underflow => {
56            return Float::log_base_power_of_2_rational_prec_round(
57                Rational::exact_from(x),
58                pow,
59                prec,
60                rm,
61            );
62        }
63        SliverOfOne::No => {}
64    }
65    // The result is never exactly representable otherwise.
66    assert_ne!(rm, Exact, "Inexact log_base_power_of_2");
67    let mut working_prec = prec + 3 + prec.ceiling_log_base_2();
68    let mut increment = Limb::WIDTH;
69    loop {
70        // log_2(x) / pow, with two correctly-rounded operations: log_base_2 (at most 1/2 ulp) and
71        // division by the exact integer pow (at most 1/2 ulp). The relative error is thus below
72        // 2^(1 - working_prec), so working_prec - 2 correct bits suffice for rounding.
73        let t = x
74            .log_base_2_prec_ref(working_prec)
75            .0
76            .div_prec(Float::from(pow), working_prec)
77            .0;
78        if float_can_round(t.significand_ref().unwrap(), working_prec - 2, prec, rm) {
79            return Float::from_float_prec_round(t, prec, rm);
80        }
81        // Increase the precision.
82        working_prec += increment;
83        increment = working_prec >> 1;
84    }
85}
86
87// The computation of log_base_power_of_2_rational(x, pow) is done by log_{2^pow}(x) = log_2(x) /
88// pow, where the input is a positive [`Rational`] that is not a power of 2. The base-2 logarithm of
89// a [`Rational`] (computed by `log_base_2_rational_prec_ref`) already handles inputs that are
90// extremely close to a power of 2 without needing extra precision, so a simple Ziv loop dividing by
91// the exact integer pow suffices here.
92fn log_base_power_of_2_rational_prec_round_helper(
93    x: &Rational,
94    pow: i64,
95    prec: u64,
96    rm: RoundingMode,
97) -> (Float, Ordering) {
98    // The initial slack keeps working_prec at least 7, so the subtraction in the rounding test
99    // below stays positive.
100    let mut working_prec = prec + 6 + prec.ceiling_log_base_2();
101    let mut increment = Limb::WIDTH;
102    loop {
103        // log_2(x) / pow, with two correctly-rounded operations: log_base_2_rational (at most 1/2
104        // ulp) and division by the exact integer pow (at most 1/2 ulp). The relative error is thus
105        // below 2^(1 - working_prec), so working_prec - 2 correct bits suffice for rounding.
106        // log_2(x) in the extended exponent range: for x within a sliver of 1 the ordinary Float
107        // form would flush to zero or clamp, and the rounding test below could never resolve it.
108        let num = extended_log_base_2_of_rational(x, working_prec);
109        let den = ExtendedFloat::from(Float::from(pow));
110        let quotient = num.div_prec_val_ref(&den, working_prec).0;
111        if float_can_round(
112            quotient.x.significand_ref().unwrap(),
113            working_prec - 4,
114            prec,
115            rm,
116        ) {
117            let (rounded, o) = Float::from_float_prec_round(quotient.x, prec, rm);
118            let mut result = ExtendedFloat::from(rounded);
119            result.exp = result.exp.checked_add(quotient.exp).unwrap();
120            return result.into_float_helper(prec, rm, o);
121        }
122        // Increase the precision.
123        working_prec += increment;
124        increment = working_prec >> 1;
125    }
126}
127
128impl Float {
129    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
130    /// integer $k$, rounding the result to the specified precision and with the specified rounding
131    /// mode. The base's exponent $k$ is `pow`, which may be negative. The [`Float`] is taken by
132    /// value. An [`Ordering`] is also returned, indicating whether the rounded value is less than,
133    /// equal to, or greater than the exact value. Although `NaN`s are not comparable to any
134    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
135    ///
136    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
137    ///
138    /// See [`RoundingMode`] for a description of the possible rounding modes.
139    ///
140    /// $$
141    /// f(x,k,p,m) = \log_{2^k} x+\varepsilon.
142    /// $$
143    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
144    ///   be 0.
145    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
146    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$.
147    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
148    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$.
149    ///
150    /// If the output has a precision, it is `prec`.
151    ///
152    /// Special cases:
153    /// - $f(\text{NaN},k,p,m)=\text{NaN}$
154    /// - $f(\infty,k,p,m)=\infty$ if $k>0$, and $-\infty$ if $k<0$
155    /// - $f(-\infty,k,p,m)=\text{NaN}$
156    /// - $f(\pm0.0,k,p,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
157    /// - $f(1.0,k,p,m)=0.0$, and the result is exact
158    /// - $f(2^m,k,p,m')=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
159    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
160    ///   is not)
161    /// - $f(x,k,p,m)=\text{NaN}$ for $x<0$
162    ///
163    /// Neither overflow nor underflow is possible.
164    ///
165    /// If you know you'll be using `Nearest`, consider using [`Float::log_base_power_of_2_prec`]
166    /// instead. If you know that your target precision is the precision of the input, consider
167    /// using [`Float::log_base_power_of_2_round`] instead. If both of these things are true,
168    /// consider using [`Float::log_base_power_of_2`] instead.
169    ///
170    /// # Worst-case complexity
171    /// $T(n) = O(n (\log n)^2 \log\log n)$
172    ///
173    /// $M(n) = O(n (\log n)^2)$
174    ///
175    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
176    ///
177    /// # Panics
178    /// Panics if `prec` is zero, if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm`
179    /// is `Exact` but the result cannot be represented exactly with the given precision. (The
180    /// result is exactly representable if and only if the input is `NaN`, infinite, zero, equal to
181    /// 1, or a power of 2 whose base-$2^k$ logarithm is representable with the given precision.)
182    ///
183    /// # Examples
184    /// ```
185    /// use malachite_base::rounding_modes::RoundingMode::*;
186    /// use malachite_float::Float;
187    /// use std::cmp::Ordering::*;
188    ///
189    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
190    ///     .0
191    ///     .log_base_power_of_2_prec_round(2, 5, Floor);
192    /// assert_eq!(log.to_string(), "1.62");
193    /// assert_eq!(o, Less);
194    ///
195    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
196    ///     .0
197    ///     .log_base_power_of_2_prec_round(2, 5, Ceiling);
198    /// assert_eq!(log.to_string(), "1.69");
199    /// assert_eq!(o, Greater);
200    ///
201    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
202    ///     .0
203    ///     .log_base_power_of_2_prec_round(2, 5, Nearest);
204    /// assert_eq!(log.to_string(), "1.69");
205    /// assert_eq!(o, Greater);
206    ///
207    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
208    ///     .0
209    ///     .log_base_power_of_2_prec_round(3, 20, Floor);
210    /// assert_eq!(log.to_string(), "1.1073093");
211    /// assert_eq!(o, Less);
212    ///
213    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
214    ///     .0
215    ///     .log_base_power_of_2_prec_round(3, 20, Ceiling);
216    /// assert_eq!(log.to_string(), "1.1073112");
217    /// assert_eq!(o, Greater);
218    ///
219    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
220    ///     .0
221    ///     .log_base_power_of_2_prec_round(3, 20, Nearest);
222    /// assert_eq!(log.to_string(), "1.1073093");
223    /// assert_eq!(o, Less);
224    ///
225    /// // log_4(8) = 3/2, exactly representable
226    /// let (log, o) = Float::from(8u32).log_base_power_of_2_prec_round(2, 10, Nearest);
227    /// assert_eq!(log.to_string(), "1.5000");
228    /// assert_eq!(o, Equal);
229    /// ```
230    #[inline]
231    pub fn log_base_power_of_2_prec_round(
232        self,
233        pow: i64,
234        prec: u64,
235        rm: RoundingMode,
236    ) -> (Self, Ordering) {
237        assert_ne!(prec, 0);
238        assert_ne!(pow, 0, "Cannot take base-1 logarithm");
239        match self {
240            Self(NaN | Infinity { sign: false } | Finite { sign: false, .. }) => {
241                (float_nan!(), Equal)
242            }
243            float_either_zero!() => (
244                if pow > 0 {
245                    float_negative_infinity!()
246                } else {
247                    float_infinity!()
248                },
249                Equal,
250            ),
251            float_infinity!() => (
252                if pow > 0 {
253                    float_infinity!()
254                } else {
255                    float_negative_infinity!()
256                },
257                Equal,
258            ),
259            _ => log_base_power_of_2_prec_round_normal(&self, pow, prec, rm),
260        }
261    }
262
263    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
264    /// integer $k$, rounding the result to the specified precision and with the specified rounding
265    /// mode. The base's exponent $k$ is `pow`, which may be negative. The [`Float`] is taken by
266    /// reference. An [`Ordering`] is also returned, indicating whether the rounded value is less
267    /// than, equal to, or greater than the exact value. Although `NaN`s are not comparable to any
268    /// [`Float`], whenever this function returns a `NaN` it also returns `Equal`.
269    ///
270    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
271    ///
272    /// See [`RoundingMode`] for a description of the possible rounding modes.
273    ///
274    /// $$
275    /// f(x,k,p,m) = \log_{2^k} x+\varepsilon.
276    /// $$
277    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
278    ///   be 0.
279    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
280    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$.
281    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
282    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$.
283    ///
284    /// If the output has a precision, it is `prec`.
285    ///
286    /// Special cases:
287    /// - $f(\text{NaN},k,p,m)=\text{NaN}$
288    /// - $f(\infty,k,p,m)=\infty$ if $k>0$, and $-\infty$ if $k<0$
289    /// - $f(-\infty,k,p,m)=\text{NaN}$
290    /// - $f(\pm0.0,k,p,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
291    /// - $f(1.0,k,p,m)=0.0$, and the result is exact
292    /// - $f(2^m,k,p,m')=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
293    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
294    ///   is not)
295    /// - $f(x,k,p,m)=\text{NaN}$ for $x<0$
296    ///
297    /// Neither overflow nor underflow is possible.
298    ///
299    /// If you know you'll be using `Nearest`, consider using
300    /// [`Float::log_base_power_of_2_prec_ref`] instead. If you know that your target precision is
301    /// the precision of the input, consider using [`Float::log_base_power_of_2_round_ref`] instead.
302    /// If both of these things are true, consider using `(&Float).log_base_power_of_2()` instead.
303    ///
304    /// # Worst-case complexity
305    /// $T(n) = O(n (\log n)^2 \log\log n)$
306    ///
307    /// $M(n) = O(n (\log n)^2)$
308    ///
309    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
310    ///
311    /// # Panics
312    /// Panics if `prec` is zero, if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm`
313    /// is `Exact` but the result cannot be represented exactly with the given precision. (The
314    /// result is exactly representable if and only if the input is `NaN`, infinite, zero, equal to
315    /// 1, or a power of 2 whose base-$2^k$ logarithm is representable with the given precision.)
316    ///
317    /// # Examples
318    /// ```
319    /// use malachite_base::rounding_modes::RoundingMode::*;
320    /// use malachite_float::Float;
321    /// use std::cmp::Ordering::*;
322    ///
323    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
324    ///     .0
325    ///     .log_base_power_of_2_prec_round_ref(2, 5, Floor);
326    /// assert_eq!(log.to_string(), "1.62");
327    /// assert_eq!(o, Less);
328    ///
329    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
330    ///     .0
331    ///     .log_base_power_of_2_prec_round_ref(2, 5, Ceiling);
332    /// assert_eq!(log.to_string(), "1.69");
333    /// assert_eq!(o, Greater);
334    ///
335    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
336    ///     .0
337    ///     .log_base_power_of_2_prec_round_ref(2, 5, Nearest);
338    /// assert_eq!(log.to_string(), "1.69");
339    /// assert_eq!(o, Greater);
340    ///
341    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
342    ///     .0
343    ///     .log_base_power_of_2_prec_round_ref(3, 20, Floor);
344    /// assert_eq!(log.to_string(), "1.1073093");
345    /// assert_eq!(o, Less);
346    ///
347    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
348    ///     .0
349    ///     .log_base_power_of_2_prec_round_ref(3, 20, Ceiling);
350    /// assert_eq!(log.to_string(), "1.1073112");
351    /// assert_eq!(o, Greater);
352    ///
353    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
354    ///     .0
355    ///     .log_base_power_of_2_prec_round_ref(3, 20, Nearest);
356    /// assert_eq!(log.to_string(), "1.1073093");
357    /// assert_eq!(o, Less);
358    ///
359    /// // log_4(8) = 3/2, exactly representable
360    /// let (log, o) = Float::from(8u32).log_base_power_of_2_prec_round_ref(2, 10, Nearest);
361    /// assert_eq!(log.to_string(), "1.5000");
362    /// assert_eq!(o, Equal);
363    /// ```
364    #[inline]
365    pub fn log_base_power_of_2_prec_round_ref(
366        &self,
367        pow: i64,
368        prec: u64,
369        rm: RoundingMode,
370    ) -> (Self, Ordering) {
371        assert_ne!(prec, 0);
372        assert_ne!(pow, 0, "Cannot take base-1 logarithm");
373        match self {
374            Self(NaN | Infinity { sign: false } | Finite { sign: false, .. }) => {
375                (float_nan!(), Equal)
376            }
377            float_either_zero!() => (
378                if pow > 0 {
379                    float_negative_infinity!()
380                } else {
381                    float_infinity!()
382                },
383                Equal,
384            ),
385            float_infinity!() => (
386                if pow > 0 {
387                    float_infinity!()
388                } else {
389                    float_negative_infinity!()
390                },
391                Equal,
392            ),
393            _ => log_base_power_of_2_prec_round_normal(self, pow, prec, rm),
394        }
395    }
396
397    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
398    /// integer $k$, rounding the result to the nearest value of the specified precision. The base's
399    /// exponent $k$ is `pow`, which may be negative. The [`Float`] is taken by value. An
400    /// [`Ordering`] is also returned, indicating whether the rounded value is less than, equal to,
401    /// or greater than the exact value. Although `NaN`s are not comparable to any [`Float`],
402    /// whenever this function returns a `NaN` it also returns `Equal`.
403    ///
404    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
405    ///
406    /// If the logarithm is equidistant from two [`Float`]s with the specified precision, the
407    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
408    /// description of the `Nearest` rounding mode.
409    ///
410    /// $$
411    /// f(x,k,p) = \log_{2^k} x+\varepsilon.
412    /// $$
413    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
414    ///   be 0.
415    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
416    ///   |\log_{2^k} x|\rfloor-p}$.
417    ///
418    /// If the output has a precision, it is `prec`.
419    ///
420    /// Special cases:
421    /// - $f(\text{NaN},k,p)=\text{NaN}$
422    /// - $f(\infty,k,p)=\infty$ if $k>0$, and $-\infty$ if $k<0$
423    /// - $f(-\infty,k,p)=\text{NaN}$
424    /// - $f(\pm0.0,k,p)=-\infty$ if $k>0$, and $\infty$ if $k<0$
425    /// - $f(1.0,k,p)=0.0$, and the result is exact
426    /// - $f(2^m,k,p)=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
427    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
428    ///   is not)
429    /// - $f(x,k,p)=\text{NaN}$ for $x<0$
430    ///
431    /// Neither overflow nor underflow is possible.
432    ///
433    /// If you want to use a rounding mode other than `Nearest`, consider using
434    /// [`Float::log_base_power_of_2_prec_round`] instead. If you know that your target precision is
435    /// the precision of the input, consider using [`Float::log_base_power_of_2`] instead.
436    ///
437    /// # Worst-case complexity
438    /// $T(n) = O(n (\log n)^2 \log\log n)$
439    ///
440    /// $M(n) = O(n (\log n)^2)$
441    ///
442    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
443    ///
444    /// # Panics
445    /// Panics if `prec` is zero or if `pow` is zero (the base $2^0=1$ has no logarithm).
446    ///
447    /// # Examples
448    /// ```
449    /// use malachite_float::Float;
450    /// use std::cmp::Ordering::*;
451    ///
452    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
453    ///     .0
454    ///     .log_base_power_of_2_prec(2, 5);
455    /// assert_eq!(log.to_string(), "1.69");
456    /// assert_eq!(o, Greater);
457    ///
458    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
459    ///     .0
460    ///     .log_base_power_of_2_prec(3, 20);
461    /// assert_eq!(log.to_string(), "1.1073093");
462    /// assert_eq!(o, Less);
463    /// ```
464    #[inline]
465    pub fn log_base_power_of_2_prec(self, pow: i64, prec: u64) -> (Self, Ordering) {
466        self.log_base_power_of_2_prec_round(pow, prec, Nearest)
467    }
468
469    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
470    /// integer $k$, rounding the result to the nearest value of the specified precision. The base's
471    /// exponent $k$ is `pow`, which may be negative. The [`Float`] is taken by reference. An
472    /// [`Ordering`] is also returned, indicating whether the rounded value is less than, equal to,
473    /// or greater than the exact value. Although `NaN`s are not comparable to any [`Float`],
474    /// whenever this function returns a `NaN` it also returns `Equal`.
475    ///
476    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
477    ///
478    /// If the logarithm is equidistant from two [`Float`]s with the specified precision, the
479    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
480    /// description of the `Nearest` rounding mode.
481    ///
482    /// $$
483    /// f(x,k,p) = \log_{2^k} x+\varepsilon.
484    /// $$
485    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
486    ///   be 0.
487    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
488    ///   |\log_{2^k} x|\rfloor-p}$.
489    ///
490    /// If the output has a precision, it is `prec`.
491    ///
492    /// Special cases:
493    /// - $f(\text{NaN},k,p)=\text{NaN}$
494    /// - $f(\infty,k,p)=\infty$ if $k>0$, and $-\infty$ if $k<0$
495    /// - $f(-\infty,k,p)=\text{NaN}$
496    /// - $f(\pm0.0,k,p)=-\infty$ if $k>0$, and $\infty$ if $k<0$
497    /// - $f(1.0,k,p)=0.0$, and the result is exact
498    /// - $f(2^m,k,p)=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
499    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
500    ///   is not)
501    /// - $f(x,k,p)=\text{NaN}$ for $x<0$
502    ///
503    /// Neither overflow nor underflow is possible.
504    ///
505    /// If you want to use a rounding mode other than `Nearest`, consider using
506    /// [`Float::log_base_power_of_2_prec_round_ref`] instead. If you know that your target
507    /// precision is the precision of the input, consider using `(&Float).log_base_power_of_2()`
508    /// instead.
509    ///
510    /// # Worst-case complexity
511    /// $T(n) = O(n (\log n)^2 \log\log n)$
512    ///
513    /// $M(n) = O(n (\log n)^2)$
514    ///
515    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
516    ///
517    /// # Panics
518    /// Panics if `prec` is zero or if `pow` is zero (the base $2^0=1$ has no logarithm).
519    ///
520    /// # Examples
521    /// ```
522    /// use malachite_float::Float;
523    /// use std::cmp::Ordering::*;
524    ///
525    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
526    ///     .0
527    ///     .log_base_power_of_2_prec_ref(2, 5);
528    /// assert_eq!(log.to_string(), "1.69");
529    /// assert_eq!(o, Greater);
530    ///
531    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
532    ///     .0
533    ///     .log_base_power_of_2_prec_ref(3, 20);
534    /// assert_eq!(log.to_string(), "1.1073093");
535    /// assert_eq!(o, Less);
536    /// ```
537    #[inline]
538    pub fn log_base_power_of_2_prec_ref(&self, pow: i64, prec: u64) -> (Self, Ordering) {
539        self.log_base_power_of_2_prec_round_ref(pow, prec, Nearest)
540    }
541
542    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
543    /// integer $k$, rounding the result with the specified rounding mode. The base's exponent $k$
544    /// is `pow`, which may be negative. The [`Float`] is taken by value. An [`Ordering`] is also
545    /// returned, indicating whether the rounded value is less than, equal to, or greater than the
546    /// exact value. Although `NaN`s are not comparable to any [`Float`], whenever this function
547    /// returns a `NaN` it also returns `Equal`.
548    ///
549    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
550    ///
551    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
552    /// description of the possible rounding modes.
553    ///
554    /// $$
555    /// f(x,k,m) = \log_{2^k} x+\varepsilon.
556    /// $$
557    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
558    ///   be 0.
559    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
560    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$, where $p$ is the precision of the input.
561    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
562    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
563    ///
564    /// If the output has a precision, it is the precision of the input.
565    ///
566    /// Special cases:
567    /// - $f(\text{NaN},k,m)=\text{NaN}$
568    /// - $f(\infty,k,m)=\infty$ if $k>0$, and $-\infty$ if $k<0$
569    /// - $f(-\infty,k,m)=\text{NaN}$
570    /// - $f(\pm0.0,k,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
571    /// - $f(1.0,k,m)=0.0$, and the result is exact
572    /// - $f(2^m,k,m')=m/k$, rounded to the precision of the input; the result is exact if and only
573    ///   if $m/k$ is representable with that precision (for example $\log_4 8=3/2$ is exact, but
574    ///   $\log_8 4=2/3$ is not)
575    /// - $f(x,k,m)=\text{NaN}$ for $x<0$
576    ///
577    /// Neither overflow nor underflow is possible.
578    ///
579    /// If you want to specify an output precision, consider using
580    /// [`Float::log_base_power_of_2_prec_round`] instead. If you know you'll be using the `Nearest`
581    /// rounding mode, consider using [`Float::log_base_power_of_2`] instead.
582    ///
583    /// # Worst-case complexity
584    /// $T(n) = O(n (\log n)^2 \log\log n)$
585    ///
586    /// $M(n) = O(n (\log n)^2)$
587    ///
588    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
589    ///
590    /// # Panics
591    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm` is `Exact` but the
592    /// result cannot be represented exactly with the input precision. (The result is exactly
593    /// representable if and only if the input is `NaN`, infinite, zero, equal to 1, or a power of 2
594    /// whose base-$2^k$ logarithm is representable with the input precision.)
595    ///
596    /// # Examples
597    /// ```
598    /// use malachite_base::rounding_modes::RoundingMode::*;
599    /// use malachite_float::Float;
600    /// use std::cmp::Ordering::*;
601    ///
602    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
603    ///     .0
604    ///     .log_base_power_of_2_round(2, Floor);
605    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147433");
606    /// assert_eq!(o, Less);
607    ///
608    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
609    ///     .0
610    ///     .log_base_power_of_2_round(2, Ceiling);
611    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147449");
612    /// assert_eq!(o, Greater);
613    ///
614    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
615    ///     .0
616    ///     .log_base_power_of_2_round(2, Nearest);
617    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147449");
618    /// assert_eq!(o, Greater);
619    /// ```
620    #[inline]
621    pub fn log_base_power_of_2_round(self, pow: i64, rm: RoundingMode) -> (Self, Ordering) {
622        let prec = self.significant_bits();
623        self.log_base_power_of_2_prec_round(pow, prec, rm)
624    }
625
626    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
627    /// integer $k$, rounding the result with the specified rounding mode. The base's exponent $k$
628    /// is `pow`, which may be negative. The [`Float`] is taken by reference. An [`Ordering`] is
629    /// also returned, indicating whether the rounded value is less than, equal to, or greater than
630    /// the exact value. Although `NaN`s are not comparable to any [`Float`], whenever this function
631    /// returns a `NaN` it also returns `Equal`.
632    ///
633    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
634    ///
635    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
636    /// description of the possible rounding modes.
637    ///
638    /// $$
639    /// f(x,k,m) = \log_{2^k} x+\varepsilon.
640    /// $$
641    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
642    ///   be 0.
643    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
644    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$, where $p$ is the precision of the input.
645    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
646    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
647    ///
648    /// If the output has a precision, it is the precision of the input.
649    ///
650    /// Special cases:
651    /// - $f(\text{NaN},k,m)=\text{NaN}$
652    /// - $f(\infty,k,m)=\infty$ if $k>0$, and $-\infty$ if $k<0$
653    /// - $f(-\infty,k,m)=\text{NaN}$
654    /// - $f(\pm0.0,k,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
655    /// - $f(1.0,k,m)=0.0$, and the result is exact
656    /// - $f(2^m,k,m')=m/k$, rounded to the precision of the input; the result is exact if and only
657    ///   if $m/k$ is representable with that precision (for example $\log_4 8=3/2$ is exact, but
658    ///   $\log_8 4=2/3$ is not)
659    /// - $f(x,k,m)=\text{NaN}$ for $x<0$
660    ///
661    /// Neither overflow nor underflow is possible.
662    ///
663    /// If you want to specify an output precision, consider using
664    /// [`Float::log_base_power_of_2_prec_round_ref`] instead. If you know you'll be using the
665    /// `Nearest` rounding mode, consider using `(&Float).log_base_power_of_2()` instead.
666    ///
667    /// # Worst-case complexity
668    /// $T(n) = O(n (\log n)^2 \log\log n)$
669    ///
670    /// $M(n) = O(n (\log n)^2)$
671    ///
672    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
673    ///
674    /// # Panics
675    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm` is `Exact` but the
676    /// result cannot be represented exactly with the input precision. (The result is exactly
677    /// representable if and only if the input is `NaN`, infinite, zero, equal to 1, or a power of 2
678    /// whose base-$2^k$ logarithm is representable with the input precision.)
679    ///
680    /// # Examples
681    /// ```
682    /// use malachite_base::rounding_modes::RoundingMode::*;
683    /// use malachite_float::Float;
684    /// use std::cmp::Ordering::*;
685    ///
686    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
687    ///     .0
688    ///     .log_base_power_of_2_round_ref(2, Floor);
689    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147433");
690    /// assert_eq!(o, Less);
691    ///
692    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
693    ///     .0
694    ///     .log_base_power_of_2_round_ref(2, Ceiling);
695    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147449");
696    /// assert_eq!(o, Greater);
697    ///
698    /// let (log, o) = Float::from_unsigned_prec(10u32, 100)
699    ///     .0
700    ///     .log_base_power_of_2_round_ref(2, Nearest);
701    /// assert_eq!(log.to_string(), "1.6609640474436811739351597147449");
702    /// assert_eq!(o, Greater);
703    /// ```
704    #[inline]
705    pub fn log_base_power_of_2_round_ref(&self, pow: i64, rm: RoundingMode) -> (Self, Ordering) {
706        let prec = self.significant_bits();
707        self.log_base_power_of_2_prec_round_ref(pow, prec, rm)
708    }
709
710    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
711    /// integer $k$, in place, rounding the result to the specified precision and with the specified
712    /// rounding mode. The base's exponent $k$ is `pow`, which may be negative. An [`Ordering`] is
713    /// returned, indicating whether the rounded value is less than, equal to, or greater than the
714    /// exact value. Although `NaN`s are not comparable to any [`Float`], whenever this function
715    /// sets the [`Float`] to `NaN` it also returns `Equal`.
716    ///
717    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
718    ///
719    /// See [`RoundingMode`] for a description of the possible rounding modes.
720    ///
721    /// $$
722    /// x \gets \log_{2^k} x+\varepsilon.
723    /// $$
724    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
725    ///   be 0.
726    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
727    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$.
728    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
729    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$.
730    ///
731    /// If the output has a precision, it is `prec`.
732    ///
733    /// See the [`Float::log_base_power_of_2_prec_round`] documentation for information on special
734    /// cases, overflow, and underflow.
735    ///
736    /// If you know you'll be using `Nearest`, consider using
737    /// [`Float::log_base_power_of_2_prec_assign`] instead. If you know that your target precision
738    /// is the precision of the input, consider using [`Float::log_base_power_of_2_round_assign`]
739    /// instead. If both of these things are true, consider using
740    /// [`Float::log_base_power_of_2_assign`] instead.
741    ///
742    /// # Worst-case complexity
743    /// $T(n) = O(n (\log n)^2 \log\log n)$
744    ///
745    /// $M(n) = O(n (\log n)^2)$
746    ///
747    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
748    ///
749    /// # Panics
750    /// Panics if `prec` is zero, if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm`
751    /// is `Exact` but the result cannot be represented exactly with the given precision. (The
752    /// result is exactly representable if and only if the input is `NaN`, infinite, zero, equal to
753    /// 1, or a power of 2 whose base-$2^k$ logarithm is representable with the given precision.)
754    ///
755    /// # Examples
756    /// ```
757    /// use malachite_base::rounding_modes::RoundingMode::*;
758    /// use malachite_float::Float;
759    /// use std::cmp::Ordering::*;
760    ///
761    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
762    /// assert_eq!(x.log_base_power_of_2_prec_round_assign(2, 5, Floor), Less);
763    /// assert_eq!(x.to_string(), "1.62");
764    ///
765    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
766    /// assert_eq!(
767    ///     x.log_base_power_of_2_prec_round_assign(2, 5, Ceiling),
768    ///     Greater
769    /// );
770    /// assert_eq!(x.to_string(), "1.69");
771    ///
772    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
773    /// assert_eq!(
774    ///     x.log_base_power_of_2_prec_round_assign(2, 5, Nearest),
775    ///     Greater
776    /// );
777    /// assert_eq!(x.to_string(), "1.69");
778    ///
779    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
780    /// assert_eq!(x.log_base_power_of_2_prec_round_assign(3, 20, Floor), Less);
781    /// assert_eq!(x.to_string(), "1.1073093");
782    ///
783    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
784    /// assert_eq!(
785    ///     x.log_base_power_of_2_prec_round_assign(3, 20, Ceiling),
786    ///     Greater
787    /// );
788    /// assert_eq!(x.to_string(), "1.1073112");
789    ///
790    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
791    /// assert_eq!(
792    ///     x.log_base_power_of_2_prec_round_assign(3, 20, Nearest),
793    ///     Less
794    /// );
795    /// assert_eq!(x.to_string(), "1.1073093");
796    /// ```
797    #[inline]
798    pub fn log_base_power_of_2_prec_round_assign(
799        &mut self,
800        pow: i64,
801        prec: u64,
802        rm: RoundingMode,
803    ) -> Ordering {
804        let (result, o) = core::mem::take(self).log_base_power_of_2_prec_round(pow, prec, rm);
805        *self = result;
806        o
807    }
808
809    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
810    /// integer $k$, in place, rounding the result to the nearest value of the specified precision.
811    /// The base's exponent $k$ is `pow`, which may be negative. An [`Ordering`] is returned,
812    /// indicating whether the rounded value is less than, equal to, or greater than the exact
813    /// value. Although `NaN`s are not comparable to any [`Float`], whenever this function sets the
814    /// [`Float`] to `NaN` it also returns `Equal`.
815    ///
816    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
817    ///
818    /// If the logarithm is equidistant from two [`Float`]s with the specified precision, the
819    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
820    /// description of the `Nearest` rounding mode.
821    ///
822    /// $$
823    /// x \gets \log_{2^k} x+\varepsilon.
824    /// $$
825    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
826    ///   be 0.
827    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
828    ///   |\log_{2^k} x|\rfloor-p}$.
829    ///
830    /// If the output has a precision, it is `prec`.
831    ///
832    /// See the [`Float::log_base_power_of_2_prec`] documentation for information on special cases,
833    /// overflow, and underflow.
834    ///
835    /// If you want to use a rounding mode other than `Nearest`, consider using
836    /// [`Float::log_base_power_of_2_prec_round_assign`] instead. If you know that your target
837    /// precision is the precision of the input, consider using
838    /// [`Float::log_base_power_of_2_assign`] instead.
839    ///
840    /// # Worst-case complexity
841    /// $T(n) = O(n (\log n)^2 \log\log n)$
842    ///
843    /// $M(n) = O(n (\log n)^2)$
844    ///
845    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
846    ///
847    /// # Panics
848    /// Panics if `prec` is zero or if `pow` is zero (the base $2^0=1$ has no logarithm).
849    ///
850    /// # Examples
851    /// ```
852    /// use malachite_float::Float;
853    /// use std::cmp::Ordering::*;
854    ///
855    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
856    /// assert_eq!(x.log_base_power_of_2_prec_assign(2, 5), Greater);
857    /// assert_eq!(x.to_string(), "1.69");
858    ///
859    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
860    /// assert_eq!(x.log_base_power_of_2_prec_assign(3, 20), Less);
861    /// assert_eq!(x.to_string(), "1.1073093");
862    /// ```
863    #[inline]
864    pub fn log_base_power_of_2_prec_assign(&mut self, pow: i64, prec: u64) -> Ordering {
865        self.log_base_power_of_2_prec_round_assign(pow, prec, Nearest)
866    }
867
868    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
869    /// integer $k$, in place, rounding the result with the specified rounding mode. The base's
870    /// exponent $k$ is `pow`, which may be negative. An [`Ordering`] is returned, indicating
871    /// whether the rounded value is less than, equal to, or greater than the exact value. Although
872    /// `NaN`s are not comparable to any [`Float`], whenever this function sets the [`Float`] to
873    /// `NaN` it also returns `Equal`.
874    ///
875    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
876    ///
877    /// The precision of the output is the precision of the input. See [`RoundingMode`] for a
878    /// description of the possible rounding modes.
879    ///
880    /// $$
881    /// x \gets \log_{2^k} x+\varepsilon.
882    /// $$
883    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
884    ///   be 0.
885    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
886    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$, where $p$ is the precision of the input.
887    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
888    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
889    ///
890    /// If the output has a precision, it is the precision of the input.
891    ///
892    /// See the [`Float::log_base_power_of_2_round`] documentation for information on special cases,
893    /// overflow, and underflow.
894    ///
895    /// If you want to specify an output precision, consider using
896    /// [`Float::log_base_power_of_2_prec_round_assign`] instead. If you know you'll be using the
897    /// `Nearest` rounding mode, consider using [`Float::log_base_power_of_2_assign`] instead.
898    ///
899    /// # Worst-case complexity
900    /// $T(n) = O(n (\log n)^2 \log\log n)$
901    ///
902    /// $M(n) = O(n (\log n)^2)$
903    ///
904    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
905    ///
906    /// # Panics
907    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm` is `Exact` but the
908    /// result cannot be represented exactly with the input precision. (The result is exactly
909    /// representable if and only if the input is `NaN`, infinite, zero, equal to 1, or a power of 2
910    /// whose base-$2^k$ logarithm is representable with the input precision.)
911    ///
912    /// # Examples
913    /// ```
914    /// use malachite_base::rounding_modes::RoundingMode::*;
915    /// use malachite_float::Float;
916    /// use std::cmp::Ordering::*;
917    ///
918    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
919    /// assert_eq!(x.log_base_power_of_2_round_assign(2, Floor), Less);
920    /// assert_eq!(x.to_string(), "1.6609640474436811739351597147433");
921    ///
922    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
923    /// assert_eq!(x.log_base_power_of_2_round_assign(2, Ceiling), Greater);
924    /// assert_eq!(x.to_string(), "1.6609640474436811739351597147449");
925    ///
926    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
927    /// assert_eq!(x.log_base_power_of_2_round_assign(2, Nearest), Greater);
928    /// assert_eq!(x.to_string(), "1.6609640474436811739351597147449");
929    /// ```
930    #[inline]
931    pub fn log_base_power_of_2_round_assign(&mut self, pow: i64, rm: RoundingMode) -> Ordering {
932        let prec = self.significant_bits();
933        self.log_base_power_of_2_prec_round_assign(pow, prec, rm)
934    }
935
936    /// Computes $\log_{2^k} x$, where $x$ is a [`Rational`] and the base is $2^k$ for some nonzero
937    /// integer $k$, rounding the result to the specified precision and with the specified rounding
938    /// mode and returning the result as a [`Float`]. The base's exponent $k$ is `pow`, which may be
939    /// negative. The [`Rational`] is taken by value. An [`Ordering`] is also returned, indicating
940    /// whether the rounded value is less than, equal to, or greater than the exact value. Although
941    /// `NaN`s are not comparable to any [`Float`], whenever this function returns a `NaN` it also
942    /// returns `Equal`.
943    ///
944    /// The base-$2^k$ logarithm of any negative number is `NaN`.
945    ///
946    /// Inputs of any magnitude are handled, including [`Rational`]s whose magnitudes are too large
947    /// or too small to be representable as [`Float`]s.
948    ///
949    /// See [`RoundingMode`] for a description of the possible rounding modes.
950    ///
951    /// $$
952    /// f(x,k,p,m) = \log_{2^k} x+\varepsilon.
953    /// $$
954    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
955    ///   be 0.
956    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
957    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$.
958    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
959    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$.
960    ///
961    /// If the output has a precision, it is `prec`.
962    ///
963    /// Special cases:
964    /// - $f(0,k,p,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
965    /// - $f(x,k,p,m)=\text{NaN}$ for $x<0$
966    /// - $f(1,k,p,m)=0.0$, and the result is exact
967    /// - $f(2^m,k,p,m')=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
968    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
969    ///   is not). This includes negative powers of 2 like $1/4$, and powers of 2 whose exponents
970    ///   $m$ lie far outside the exponent range of [`Float`].
971    ///
972    /// If you know you'll be using `Nearest`, consider using
973    /// [`Float::log_base_power_of_2_rational_prec`] instead.
974    ///
975    /// # Worst-case complexity
976    /// $T(n) = O(n (\log n)^2 \log\log n)$
977    ///
978    /// $M(n) = O(n (\log n)^2)$
979    ///
980    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
981    ///
982    /// # Panics
983    /// Panics if `prec` is zero, if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm`
984    /// is `Exact` but the result cannot be represented exactly with the given precision. (The
985    /// result is exactly representable if and only if $x\leq 0$ or $x$ is a power of 2 whose
986    /// base-$2^k$ logarithm is representable with the given precision.)
987    ///
988    /// # Examples
989    /// ```
990    /// use malachite_base::rounding_modes::RoundingMode::*;
991    /// use malachite_float::Float;
992    /// use malachite_q::Rational;
993    /// use std::cmp::Ordering::*;
994    ///
995    /// let (log, o) = Float::log_base_power_of_2_rational_prec_round(
996    ///     Rational::from_unsigneds(3u8, 5),
997    ///     2,
998    ///     20,
999    ///     Floor,
1000    /// );
1001    /// assert_eq!(log.to_string(), "-0.36848307");
1002    /// assert_eq!(o, Less);
1003    ///
1004    /// let (log, o) = Float::log_base_power_of_2_rational_prec_round(
1005    ///     Rational::from_unsigneds(3u8, 5),
1006    ///     2,
1007    ///     20,
1008    ///     Ceiling,
1009    /// );
1010    /// assert_eq!(log.to_string(), "-0.36848259");
1011    /// assert_eq!(o, Greater);
1012    /// ```
1013    #[allow(clippy::needless_pass_by_value)]
1014    #[inline]
1015    pub fn log_base_power_of_2_rational_prec_round(
1016        x: Rational,
1017        pow: i64,
1018        prec: u64,
1019        rm: RoundingMode,
1020    ) -> (Self, Ordering) {
1021        Self::log_base_power_of_2_rational_prec_round_ref(&x, pow, prec, rm)
1022    }
1023
1024    /// Computes $\log_{2^k} x$, where $x$ is a [`Rational`] and the base is $2^k$ for some nonzero
1025    /// integer $k$, rounding the result to the specified precision and with the specified rounding
1026    /// mode and returning the result as a [`Float`]. The base's exponent $k$ is `pow`, which may be
1027    /// negative. The [`Rational`] is taken by reference. An [`Ordering`] is also returned,
1028    /// indicating whether the rounded value is less than, equal to, or greater than the exact
1029    /// value. Although `NaN`s are not comparable to any [`Float`], whenever this function returns a
1030    /// `NaN` it also returns `Equal`.
1031    ///
1032    /// The base-$2^k$ logarithm of any negative number is `NaN`.
1033    ///
1034    /// Inputs of any magnitude are handled, including [`Rational`]s whose magnitudes are too large
1035    /// or too small to be representable as [`Float`]s.
1036    ///
1037    /// See [`RoundingMode`] for a description of the possible rounding modes.
1038    ///
1039    /// $$
1040    /// f(x,k,p,m) = \log_{2^k} x+\varepsilon.
1041    /// $$
1042    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1043    ///   be 0.
1044    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is not `Nearest`, then $|\varepsilon| <
1045    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p+1}$.
1046    /// - If $\log_{2^k} x$ is finite and nonzero, and $m$ is `Nearest`, then $|\varepsilon| \leq
1047    ///   2^{\lfloor\log_2 |\log_{2^k} x|\rfloor-p}$.
1048    ///
1049    /// If the output has a precision, it is `prec`.
1050    ///
1051    /// Special cases:
1052    /// - $f(0,k,p,m)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1053    /// - $f(x,k,p,m)=\text{NaN}$ for $x<0$
1054    /// - $f(1,k,p,m)=0.0$, and the result is exact
1055    /// - $f(2^m,k,p,m')=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
1056    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
1057    ///   is not). This includes negative powers of 2 like $1/4$, and powers of 2 whose exponents
1058    ///   $m$ lie far outside the exponent range of [`Float`].
1059    ///
1060    /// If you know you'll be using `Nearest`, consider using
1061    /// [`Float::log_base_power_of_2_rational_prec_ref`] instead.
1062    ///
1063    /// # Worst-case complexity
1064    /// $T(n) = O(n (\log n)^2 \log\log n)$
1065    ///
1066    /// $M(n) = O(n (\log n)^2)$
1067    ///
1068    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1069    ///
1070    /// # Panics
1071    /// Panics if `prec` is zero, if `pow` is zero (the base $2^0=1$ has no logarithm), or if `rm`
1072    /// is `Exact` but the result cannot be represented exactly with the given precision. (The
1073    /// result is exactly representable if and only if $x\leq 0$ or $x$ is a power of 2 whose
1074    /// base-$2^k$ logarithm is representable with the given precision.)
1075    ///
1076    /// # Examples
1077    /// ```
1078    /// use malachite_base::rounding_modes::RoundingMode::*;
1079    /// use malachite_float::Float;
1080    /// use malachite_q::Rational;
1081    /// use std::cmp::Ordering::*;
1082    ///
1083    /// let (log, o) = Float::log_base_power_of_2_rational_prec_round_ref(
1084    ///     &Rational::from_unsigneds(3u8, 5),
1085    ///     2,
1086    ///     20,
1087    ///     Floor,
1088    /// );
1089    /// assert_eq!(log.to_string(), "-0.36848307");
1090    /// assert_eq!(o, Less);
1091    ///
1092    /// let (log, o) = Float::log_base_power_of_2_rational_prec_round_ref(
1093    ///     &Rational::from_unsigneds(3u8, 5),
1094    ///     2,
1095    ///     20,
1096    ///     Ceiling,
1097    /// );
1098    /// assert_eq!(log.to_string(), "-0.36848259");
1099    /// assert_eq!(o, Greater);
1100    ///
1101    /// // log_4(8) = 3/2, exactly representable
1102    /// let (log, o) = Float::log_base_power_of_2_rational_prec_round_ref(
1103    ///     &Rational::from(8u32),
1104    ///     2,
1105    ///     10,
1106    ///     Nearest,
1107    /// );
1108    /// assert_eq!(log.to_string(), "1.5000");
1109    /// assert_eq!(o, Equal);
1110    /// ```
1111    pub fn log_base_power_of_2_rational_prec_round_ref(
1112        x: &Rational,
1113        pow: i64,
1114        prec: u64,
1115        rm: RoundingMode,
1116    ) -> (Self, Ordering) {
1117        assert_ne!(prec, 0);
1118        assert_ne!(pow, 0, "Cannot take base-1 logarithm");
1119        match x.sign() {
1120            Equal => {
1121                return (
1122                    if pow > 0 {
1123                        float_negative_infinity!()
1124                    } else {
1125                        float_infinity!()
1126                    },
1127                    Equal,
1128                );
1129            }
1130            Less => return (float_nan!(), Equal),
1131            Greater => {}
1132        }
1133        // If x is 2^m, then log_2(x) = m and the result is the rational m / pow (exact when
1134        // representable at the target precision).
1135        if let Some(m) = x.checked_log_base_2() {
1136            return Self::from(m).div_prec_round(Self::from(pow), prec, rm);
1137        }
1138        // The result is never exactly representable otherwise.
1139        assert_ne!(rm, Exact, "Inexact log_base_power_of_2");
1140        log_base_power_of_2_rational_prec_round_helper(x, pow, prec, rm)
1141    }
1142
1143    /// Computes $\log_{2^k} x$, where $x$ is a [`Rational`] and the base is $2^k$ for some nonzero
1144    /// integer $k$, rounding the result to the nearest value of the specified precision and
1145    /// returning the result as a [`Float`]. The base's exponent $k$ is `pow`, which may be
1146    /// negative. The [`Rational`] is taken by value. An [`Ordering`] is also returned, indicating
1147    /// whether the rounded value is less than, equal to, or greater than the exact value. Although
1148    /// `NaN`s are not comparable to any [`Float`], whenever this function returns a `NaN` it also
1149    /// returns `Equal`.
1150    ///
1151    /// The base-$2^k$ logarithm of any negative number is `NaN`.
1152    ///
1153    /// Inputs of any magnitude are handled, including [`Rational`]s whose magnitudes are too large
1154    /// or too small to be representable as [`Float`]s.
1155    ///
1156    /// If the logarithm is equidistant from two [`Float`]s with the specified precision, the
1157    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1158    /// description of the `Nearest` rounding mode.
1159    ///
1160    /// $$
1161    /// f(x,k,p) = \log_{2^k} x+\varepsilon.
1162    /// $$
1163    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1164    ///   be 0.
1165    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
1166    ///   |\log_{2^k} x|\rfloor-p}$.
1167    ///
1168    /// If the output has a precision, it is `prec`.
1169    ///
1170    /// Special cases:
1171    /// - $f(0,k,p)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1172    /// - $f(x,k,p)=\text{NaN}$ for $x<0$
1173    /// - $f(1,k,p)=0.0$, and the result is exact
1174    /// - $f(2^m,k,p)=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
1175    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
1176    ///   is not). This includes negative powers of 2 like $1/4$, and powers of 2 whose exponents
1177    ///   $m$ lie far outside the exponent range of [`Float`].
1178    ///
1179    /// If you want to use a rounding mode other than `Nearest`, consider using
1180    /// [`Float::log_base_power_of_2_rational_prec_round`] instead.
1181    ///
1182    /// # Worst-case complexity
1183    /// $T(n) = O(n (\log n)^2 \log\log n)$
1184    ///
1185    /// $M(n) = O(n (\log n)^2)$
1186    ///
1187    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1188    ///
1189    /// # Panics
1190    /// Panics if `prec` is zero or if `pow` is zero (the base $2^0=1$ has no logarithm).
1191    ///
1192    /// # Examples
1193    /// ```
1194    /// use malachite_float::Float;
1195    /// use malachite_q::Rational;
1196    /// use std::cmp::Ordering::*;
1197    ///
1198    /// let (log, o) =
1199    ///     Float::log_base_power_of_2_rational_prec(Rational::from_unsigneds(3u8, 5), 2, 20);
1200    /// assert_eq!(log.to_string(), "-0.36848259");
1201    /// assert_eq!(o, Greater);
1202    /// ```
1203    #[inline]
1204    pub fn log_base_power_of_2_rational_prec(x: Rational, pow: i64, prec: u64) -> (Self, Ordering) {
1205        Self::log_base_power_of_2_rational_prec_round(x, pow, prec, Nearest)
1206    }
1207
1208    /// Computes $\log_{2^k} x$, where $x$ is a [`Rational`] and the base is $2^k$ for some nonzero
1209    /// integer $k$, rounding the result to the nearest value of the specified precision and
1210    /// returning the result as a [`Float`]. The base's exponent $k$ is `pow`, which may be
1211    /// negative. The [`Rational`] is taken by reference. An [`Ordering`] is also returned,
1212    /// indicating whether the rounded value is less than, equal to, or greater than the exact
1213    /// value. Although `NaN`s are not comparable to any [`Float`], whenever this function returns a
1214    /// `NaN` it also returns `Equal`.
1215    ///
1216    /// The base-$2^k$ logarithm of any negative number is `NaN`.
1217    ///
1218    /// Inputs of any magnitude are handled, including [`Rational`]s whose magnitudes are too large
1219    /// or too small to be representable as [`Float`]s.
1220    ///
1221    /// If the logarithm is equidistant from two [`Float`]s with the specified precision, the
1222    /// [`Float`] with fewer 1s in its binary expansion is chosen. See [`RoundingMode`] for a
1223    /// description of the `Nearest` rounding mode.
1224    ///
1225    /// $$
1226    /// f(x,k,p) = \log_{2^k} x+\varepsilon.
1227    /// $$
1228    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1229    ///   be 0.
1230    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
1231    ///   |\log_{2^k} x|\rfloor-p}$.
1232    ///
1233    /// If the output has a precision, it is `prec`.
1234    ///
1235    /// Special cases:
1236    /// - $f(0,k,p)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1237    /// - $f(x,k,p)=\text{NaN}$ for $x<0$
1238    /// - $f(1,k,p)=0.0$, and the result is exact
1239    /// - $f(2^m,k,p)=m/k$, rounded to precision $p$; the result is exact if and only if $m/k$ is
1240    ///   representable with precision $p$ (for example $\log_4 8=3/2$ is exact, but $\log_8 4=2/3$
1241    ///   is not). This includes negative powers of 2 like $1/4$, and powers of 2 whose exponents
1242    ///   $m$ lie far outside the exponent range of [`Float`].
1243    ///
1244    /// If you want to use a rounding mode other than `Nearest`, consider using
1245    /// [`Float::log_base_power_of_2_rational_prec_round_ref`] instead.
1246    ///
1247    /// # Worst-case complexity
1248    /// $T(n) = O(n (\log n)^2 \log\log n)$
1249    ///
1250    /// $M(n) = O(n (\log n)^2)$
1251    ///
1252    /// where $T$ is time, $M$ is additional memory, and $n$ is `prec`.
1253    ///
1254    /// # Panics
1255    /// Panics if `prec` is zero or if `pow` is zero (the base $2^0=1$ has no logarithm).
1256    ///
1257    /// # Examples
1258    /// ```
1259    /// use malachite_float::Float;
1260    /// use malachite_q::Rational;
1261    /// use std::cmp::Ordering::*;
1262    ///
1263    /// let (log, o) =
1264    ///     Float::log_base_power_of_2_rational_prec_ref(&Rational::from_unsigneds(3u8, 5), 2, 20);
1265    /// assert_eq!(log.to_string(), "-0.36848259");
1266    /// assert_eq!(o, Greater);
1267    /// ```
1268    #[inline]
1269    pub fn log_base_power_of_2_rational_prec_ref(
1270        x: &Rational,
1271        pow: i64,
1272        prec: u64,
1273    ) -> (Self, Ordering) {
1274        Self::log_base_power_of_2_rational_prec_round_ref(x, pow, prec, Nearest)
1275    }
1276}
1277
1278impl LogBasePowerOf2<i64> for Float {
1279    type Output = Self;
1280
1281    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
1282    /// integer $k$, taking it by value. The base's exponent $k$ is `pow`, which may be negative.
1283    ///
1284    /// If the output has a precision, it is the precision of the input. If the logarithm is
1285    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1286    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1287    /// rounding mode.
1288    ///
1289    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
1290    ///
1291    /// $$
1292    /// f(x,k) = \log_{2^k} x+\varepsilon.
1293    /// $$
1294    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1295    ///   be 0.
1296    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
1297    ///   |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
1298    ///
1299    /// Special cases:
1300    /// - $f(\text{NaN},k)=\text{NaN}$
1301    /// - $f(\infty,k)=\infty$ if $k>0$, and $-\infty$ if $k<0$
1302    /// - $f(-\infty,k)=\text{NaN}$
1303    /// - $f(\pm0.0,k)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1304    /// - $f(1.0,k)=0.0$, and the result is exact
1305    /// - $f(2^m,k)=m/k$, rounded to the precision of the input; the result is exact if and only if
1306    ///   $m/k$ is representable with that precision (for example $\log_4 8=3/2$ is exact, but
1307    ///   $\log_8 4=2/3$ is not)
1308    /// - $f(x,k)=\text{NaN}$ for $x<0$
1309    ///
1310    /// Neither overflow nor underflow is possible.
1311    ///
1312    /// If you want to use a rounding mode other than `Nearest`, consider using
1313    /// [`Float::log_base_power_of_2_round`] instead. If you want to specify the output precision,
1314    /// consider using [`Float::log_base_power_of_2_prec`]. If you want both of these things,
1315    /// consider using [`Float::log_base_power_of_2_prec_round`].
1316    ///
1317    /// # Worst-case complexity
1318    /// $T(n) = O(n (\log n)^2 \log\log n)$
1319    ///
1320    /// $M(n) = O(n (\log n)^2)$
1321    ///
1322    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
1323    ///
1324    /// # Panics
1325    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm).
1326    ///
1327    /// # Examples
1328    /// ```
1329    /// use malachite_base::num::arithmetic::traits::LogBasePowerOf2;
1330    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity};
1331    /// use malachite_float::Float;
1332    ///
1333    /// assert!(Float::NAN.log_base_power_of_2(2).is_nan());
1334    /// assert_eq!(Float::INFINITY.log_base_power_of_2(2), Float::INFINITY);
1335    /// assert_eq!(
1336    ///     Float::INFINITY.log_base_power_of_2(-2),
1337    ///     Float::NEGATIVE_INFINITY
1338    /// );
1339    /// assert!(Float::NEGATIVE_INFINITY.log_base_power_of_2(2).is_nan());
1340    /// assert_eq!(
1341    ///     Float::from_unsigned_prec(10u32, 100)
1342    ///         .0
1343    ///         .log_base_power_of_2(2)
1344    ///         .to_string(),
1345    ///     "1.6609640474436811739351597147449"
1346    /// );
1347    /// assert!(Float::from_signed_prec(-10, 100)
1348    ///     .0
1349    ///     .log_base_power_of_2(2)
1350    ///     .is_nan());
1351    /// ```
1352    #[inline]
1353    fn log_base_power_of_2(self, pow: i64) -> Self {
1354        let prec = self.significant_bits();
1355        self.log_base_power_of_2_prec_round(pow, prec, Nearest).0
1356    }
1357}
1358
1359impl LogBasePowerOf2<i64> for &Float {
1360    type Output = Float;
1361
1362    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
1363    /// integer $k$, taking it by reference. The base's exponent $k$ is `pow`, which may be
1364    /// negative.
1365    ///
1366    /// If the output has a precision, it is the precision of the input. If the logarithm is
1367    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1368    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1369    /// rounding mode.
1370    ///
1371    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
1372    ///
1373    /// $$
1374    /// f(x,k) = \log_{2^k} x+\varepsilon.
1375    /// $$
1376    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1377    ///   be 0.
1378    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
1379    ///   |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
1380    ///
1381    /// Special cases:
1382    /// - $f(\text{NaN},k)=\text{NaN}$
1383    /// - $f(\infty,k)=\infty$ if $k>0$, and $-\infty$ if $k<0$
1384    /// - $f(-\infty,k)=\text{NaN}$
1385    /// - $f(\pm0.0,k)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1386    /// - $f(1.0,k)=0.0$, and the result is exact
1387    /// - $f(2^m,k)=m/k$, rounded to the precision of the input; the result is exact if and only if
1388    ///   $m/k$ is representable with that precision (for example $\log_4 8=3/2$ is exact, but
1389    ///   $\log_8 4=2/3$ is not)
1390    /// - $f(x,k)=\text{NaN}$ for $x<0$
1391    ///
1392    /// Neither overflow nor underflow is possible.
1393    ///
1394    /// If you want to use a rounding mode other than `Nearest`, consider using
1395    /// [`Float::log_base_power_of_2_round_ref`] instead. If you want to specify the output
1396    /// precision, consider using [`Float::log_base_power_of_2_prec_ref`]. If you want both of these
1397    /// things, consider using [`Float::log_base_power_of_2_prec_round_ref`].
1398    ///
1399    /// # Worst-case complexity
1400    /// $T(n) = O(n (\log n)^2 \log\log n)$
1401    ///
1402    /// $M(n) = O(n (\log n)^2)$
1403    ///
1404    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
1405    ///
1406    /// # Panics
1407    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm).
1408    ///
1409    /// # Examples
1410    /// ```
1411    /// use malachite_base::num::arithmetic::traits::LogBasePowerOf2;
1412    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity};
1413    /// use malachite_float::Float;
1414    ///
1415    /// assert!((&Float::NAN).log_base_power_of_2(2).is_nan());
1416    /// assert_eq!((&Float::INFINITY).log_base_power_of_2(2), Float::INFINITY);
1417    /// assert_eq!(
1418    ///     (&Float::INFINITY).log_base_power_of_2(-2),
1419    ///     Float::NEGATIVE_INFINITY
1420    /// );
1421    /// assert!((&Float::NEGATIVE_INFINITY).log_base_power_of_2(2).is_nan());
1422    /// assert_eq!(
1423    ///     (&Float::from_unsigned_prec(10u32, 100).0)
1424    ///         .log_base_power_of_2(2)
1425    ///         .to_string(),
1426    ///     "1.6609640474436811739351597147449"
1427    /// );
1428    /// assert!((&Float::from_signed_prec(-10, 100).0)
1429    ///     .log_base_power_of_2(2)
1430    ///     .is_nan());
1431    /// ```
1432    #[inline]
1433    fn log_base_power_of_2(self, pow: i64) -> Float {
1434        let prec = self.significant_bits();
1435        self.log_base_power_of_2_prec_round_ref(pow, prec, Nearest)
1436            .0
1437    }
1438}
1439
1440impl LogBasePowerOf2Assign<i64> for Float {
1441    /// Computes $\log_{2^k} x$, where $x$ is a [`Float`] and the base is $2^k$ for some nonzero
1442    /// integer $k$, in place. The base's exponent $k$ is `pow`, which may be negative.
1443    ///
1444    /// If the output has a precision, it is the precision of the input. If the logarithm is
1445    /// equidistant from two [`Float`]s with the specified precision, the [`Float`] with fewer 1s in
1446    /// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest`
1447    /// rounding mode.
1448    ///
1449    /// The base-$2^k$ logarithm of any nonzero negative number is `NaN`.
1450    ///
1451    /// $$
1452    /// x \gets \log_{2^k} x+\varepsilon.
1453    /// $$
1454    /// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to
1455    ///   be 0.
1456    /// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| \leq 2^{\lfloor\log_2
1457    ///   |\log_{2^k} x|\rfloor-p}$, where $p$ is the precision of the input.
1458    ///
1459    /// See the [`Float::log_base_power_of_2`] documentation for information on special cases,
1460    /// overflow, and underflow.
1461    ///
1462    /// If you want to use a rounding mode other than `Nearest`, consider using
1463    /// [`Float::log_base_power_of_2_round_assign`] instead. If you want to specify the output
1464    /// precision, consider using [`Float::log_base_power_of_2_prec_assign`]. If you want both of
1465    /// these things, consider using [`Float::log_base_power_of_2_prec_round_assign`].
1466    ///
1467    /// # Worst-case complexity
1468    /// $T(n) = O(n (\log n)^2 \log\log n)$
1469    ///
1470    /// $M(n) = O(n (\log n)^2)$
1471    ///
1472    /// where $T$ is time, $M$ is additional memory, and $n$ is `self.get_prec()`.
1473    ///
1474    /// # Panics
1475    /// Panics if `pow` is zero (the base $2^0=1$ has no logarithm).
1476    ///
1477    /// # Examples
1478    /// ```
1479    /// use malachite_base::num::arithmetic::traits::LogBasePowerOf2Assign;
1480    /// use malachite_base::num::basic::traits::{Infinity, NaN, NegativeInfinity};
1481    /// use malachite_float::Float;
1482    ///
1483    /// let mut x = Float::NAN;
1484    /// x.log_base_power_of_2_assign(2);
1485    /// assert!(x.is_nan());
1486    ///
1487    /// let mut x = Float::INFINITY;
1488    /// x.log_base_power_of_2_assign(2);
1489    /// assert_eq!(x, Float::INFINITY);
1490    ///
1491    /// let mut x = Float::INFINITY;
1492    /// x.log_base_power_of_2_assign(-2);
1493    /// assert_eq!(x, Float::NEGATIVE_INFINITY);
1494    ///
1495    /// let mut x = Float::NEGATIVE_INFINITY;
1496    /// x.log_base_power_of_2_assign(2);
1497    /// assert!(x.is_nan());
1498    ///
1499    /// let mut x = Float::from_unsigned_prec(10u32, 100).0;
1500    /// x.log_base_power_of_2_assign(2);
1501    /// assert_eq!(x.to_string(), "1.6609640474436811739351597147449");
1502    ///
1503    /// let mut x = Float::from_signed_prec(-10, 100).0;
1504    /// x.log_base_power_of_2_assign(2);
1505    /// assert!(x.is_nan());
1506    /// ```
1507    #[inline]
1508    fn log_base_power_of_2_assign(&mut self, pow: i64) {
1509        let prec = self.significant_bits();
1510        self.log_base_power_of_2_prec_round_assign(pow, prec, Nearest);
1511    }
1512}
1513
1514/// Computes $\log_{2^k} x$, the base-$2^k$ logarithm of a primitive float, where the base is $2^k$
1515/// for some nonzero integer $k$. The exponent $k$ is `pow`, which may be negative. Using this
1516/// function is more accurate than computing the logarithm using the standard library, whose `log2`
1517/// is not always correctly rounded.
1518///
1519/// The base-$2^k$ logarithm of any negative number is `NaN`.
1520///
1521/// $$
1522/// f(x,k) = \log_{2^k} x+\varepsilon.
1523/// $$
1524/// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be
1525///   0.
1526/// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 |\log_{2^k}
1527///   x|\rfloor-p}$, where $p$ is precision of the output (typically 24 if `T` is a [`f32`] and 53
1528///   if `T` is a [`f64`], but less if the output is subnormal).
1529///
1530/// Special cases:
1531/// - $f(\text{NaN},k)=\text{NaN}$
1532/// - $f(\infty,k)=\infty$ if $k>0$, and $-\infty$ if $k<0$
1533/// - $f(-\infty,k)=\text{NaN}$
1534/// - $f(\pm0.0,k)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1535/// - $f(1.0,k)=0.0$
1536/// - $f(x,k)=\text{NaN}$ for $x<0$
1537///
1538/// Neither overflow nor underflow is possible.
1539///
1540/// # Worst-case complexity
1541/// Constant time and additional memory.
1542///
1543/// # Panics
1544/// Panics if `pow` is zero (the base $2^0=1$ has no logarithm).
1545///
1546/// # Examples
1547/// ```
1548/// use malachite_base::num::float::NiceFloat;
1549/// use malachite_float::float::arithmetic::log_base_power_of_2::*;
1550///
1551/// assert!(primitive_float_log_base_power_of_2(f32::NAN, 2).is_nan());
1552/// // log_4(16) = 2
1553/// assert_eq!(
1554///     NiceFloat(primitive_float_log_base_power_of_2(16.0f32, 2)),
1555///     NiceFloat(2.0)
1556/// );
1557/// // log_4(8) = 3/2
1558/// assert_eq!(
1559///     NiceFloat(primitive_float_log_base_power_of_2(8.0f32, 2)),
1560///     NiceFloat(1.5)
1561/// );
1562/// // log_8(64) = 2
1563/// assert_eq!(
1564///     NiceFloat(primitive_float_log_base_power_of_2(64.0f32, 3)),
1565///     NiceFloat(2.0)
1566/// );
1567/// // log_4(10)
1568/// assert_eq!(
1569///     NiceFloat(primitive_float_log_base_power_of_2(10.0f32, 2)),
1570///     NiceFloat(1.660964)
1571/// );
1572/// // log_(1/2)(8) = -3
1573/// assert_eq!(
1574///     NiceFloat(primitive_float_log_base_power_of_2(8.0f32, -1)),
1575///     NiceFloat(-3.0)
1576/// );
1577/// ```
1578#[inline]
1579#[allow(clippy::type_repetition_in_bounds)]
1580pub fn primitive_float_log_base_power_of_2<T: PrimitiveFloat>(x: T, pow: i64) -> T
1581where
1582    Float: From<T> + PartialOrd<T>,
1583    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
1584{
1585    emulate_float_to_float_fn(|x, prec| Float::log_base_power_of_2_prec(x, pow, prec), x)
1586}
1587
1588/// Computes $\log_{2^k} x$, the base-$2^k$ logarithm of a [`Rational`], where the base is $2^k$ for
1589/// some nonzero integer $k$, returning a primitive float result. The exponent $k$ is `pow`, which
1590/// may be negative.
1591///
1592/// If the logarithm is equidistant from two primitive floats, the primitive float with fewer 1s in
1593/// its binary expansion is chosen. See [`RoundingMode`] for a description of the `Nearest` rounding
1594/// mode.
1595///
1596/// The base-$2^k$ logarithm of any negative number is `NaN`.
1597///
1598/// $$
1599/// f(x,k) = \log_{2^k} x+\varepsilon.
1600/// $$
1601/// - If $\log_{2^k} x$ is infinite, zero, or `NaN`, $\varepsilon$ may be ignored or assumed to be
1602///   0.
1603/// - If $\log_{2^k} x$ is finite and nonzero, then $|\varepsilon| < 2^{\lfloor\log_2 |\log_{2^k}
1604///   x|\rfloor-p}$, where $p$ is precision of the output (typically 24 if `T` is a [`f32`] and 53
1605///   if `T` is a [`f64`], but less if the output is subnormal).
1606///
1607/// Special cases:
1608/// - $f(0,k)=-\infty$ if $k>0$, and $\infty$ if $k<0$
1609/// - $f(x,k)=\text{NaN}$ for $x<0$
1610/// - $f(1,k)=0.0$
1611///
1612/// Neither overflow nor underflow is possible.
1613///
1614/// # Worst-case complexity
1615/// Constant time and additional memory.
1616///
1617/// # Panics
1618/// Panics if `pow` is zero (the base $2^0=1$ has no logarithm).
1619///
1620/// # Examples
1621/// ```
1622/// use malachite_base::num::basic::traits::{NegativeInfinity, Zero};
1623/// use malachite_base::num::float::NiceFloat;
1624/// use malachite_float::float::arithmetic::log_base_power_of_2::*;
1625/// use malachite_q::Rational;
1626///
1627/// assert_eq!(
1628///     NiceFloat(primitive_float_log_base_power_of_2_rational::<f64>(
1629///         &Rational::ZERO,
1630///         2
1631///     )),
1632///     NiceFloat(f64::NEGATIVE_INFINITY)
1633/// );
1634/// assert_eq!(
1635///     NiceFloat(primitive_float_log_base_power_of_2_rational::<f64>(
1636///         &Rational::ZERO,
1637///         -2
1638///     )),
1639///     NiceFloat(f64::INFINITY)
1640/// );
1641/// // log_4(1/3)
1642/// assert_eq!(
1643///     NiceFloat(primitive_float_log_base_power_of_2_rational::<f64>(
1644///         &Rational::from_unsigneds(1u8, 3),
1645///         2
1646///     )),
1647///     NiceFloat(-0.792481250360578)
1648/// );
1649/// // log_4(10000)
1650/// assert_eq!(
1651///     NiceFloat(primitive_float_log_base_power_of_2_rational::<f64>(
1652///         &Rational::from(10000),
1653///         2
1654///     )),
1655///     NiceFloat(6.643856189774724)
1656/// );
1657/// assert_eq!(
1658///     NiceFloat(primitive_float_log_base_power_of_2_rational::<f64>(
1659///         &Rational::from(-10000),
1660///         2
1661///     )),
1662///     NiceFloat(f64::NAN)
1663/// );
1664/// ```
1665#[inline]
1666#[allow(clippy::type_repetition_in_bounds)]
1667pub fn primitive_float_log_base_power_of_2_rational<T: PrimitiveFloat>(x: &Rational, pow: i64) -> T
1668where
1669    Float: PartialOrd<T>,
1670    for<'a> T: ExactFrom<&'a Float> + RoundingFrom<&'a Float>,
1671{
1672    emulate_rational_to_float_fn(
1673        |x, prec| Float::log_base_power_of_2_rational_prec_ref(x, pow, prec),
1674        x,
1675    )
1676}