use malachite_base::num::arithmetic::traits::{IsPowerOf2, PowerOf2, ShlRound, UnsignedAbs};
use malachite_base::num::basic::signeds::PrimitiveSigned;
use malachite_base::num::basic::traits::{
Infinity, NaN, NegativeInfinity, NegativeZero, One, Zero,
};
use malachite_base::num::basic::unsigneds::PrimitiveUnsigned;
use malachite_base::num::comparison::traits::PartialOrdAbs;
use malachite_base::num::conversion::traits::ExactFrom;
use malachite_base::rounding_modes::RoundingMode::*;
use malachite_base::test_util::generators::{
signed_gen, signed_gen_var_5, unsigned_gen, unsigned_gen_var_5,
};
use malachite_float::test_util::arithmetic::shl::shl_naive;
use malachite_float::test_util::common::{parse_hex_string, to_hex_string};
use malachite_float::test_util::generators::{
float_gen, float_signed_pair_gen_var_2, float_signed_pair_gen_var_3,
float_unsigned_pair_gen_var_2, float_unsigned_pair_gen_var_3,
};
use malachite_float::{ComparableFloat, ComparableFloatRef, Float};
use malachite_nz::integer::Integer;
use malachite_nz::test_util::generators::integer_unsigned_pair_gen_var_2;
use malachite_q::Rational;
use std::ops::{Shl, ShlAssign, Shr};
fn test_shl_unsigned_helper<T: PrimitiveUnsigned, F: Fn(Float, T, Float)>(f: F)
where
Float: ShlAssign<T> + Shl<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>,
{
let test = |s, s_hex, v: u64, out: &str, out_hex: &str| {
let x = parse_hex_string(s_hex);
assert_eq!(x.to_string(), s);
let v = T::exact_from(v);
let mut n = x.clone();
n <<= v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = x.clone() << v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = &x << v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = shl_naive(x.clone(), v);
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
f(x, v, n);
};
test("NaN", "NaN", 0, "NaN", "NaN");
test("NaN", "NaN", 10, "NaN", "NaN");
test("Infinity", "Infinity", 0, "Infinity", "Infinity");
test("Infinity", "Infinity", 10, "Infinity", "Infinity");
test("-Infinity", "-Infinity", 0, "-Infinity", "-Infinity");
test("-Infinity", "-Infinity", 10, "-Infinity", "-Infinity");
test("0.0", "0x0.0", 10, "0.0", "0x0.0");
test("-0.0", "-0x0.0", 10, "-0.0", "-0x0.0");
test("123.0", "0x7b.0#7", 0, "123.0", "0x7b.0#7");
test("123.0", "0x7b.0#7", 1, "246.0", "0xf6.0#7");
test("123.0", "0x7b.0#7", 10, "1.26e5", "0x1.ecE+4#7");
test("123.0", "0x7b.0#7", 100, "1.56e32", "0x7.bE+26#7");
test("-123.0", "-0x7b.0#7", 0, "-123.0", "-0x7b.0#7");
test("-123.0", "-0x7b.0#7", 1, "-246.0", "-0xf6.0#7");
test("-123.0", "-0x7b.0#7", 10, "-1.26e5", "-0x1.ecE+4#7");
test("-123.0", "-0x7b.0#7", 100, "-1.56e32", "-0x7.bE+26#7");
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
0,
"3.1415926535897931",
"0x3.243f6a8885a30#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
1,
"6.283185307179586",
"0x6.487ed5110b460#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
10,
"3216.9908772759482",
"0xc90.fdaa22168c0#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
100,
"3.9824418129956972e30",
"0x3.243f6a8885a30E+25#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
0,
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
1,
"-6.283185307179586",
"-0x6.487ed5110b460#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
10,
"-3216.9908772759482",
"-0xc90.fdaa22168c0#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
100,
"-3.9824418129956972e30",
"-0x3.243f6a8885a30E+25#53",
);
let test_extreme = |s, s_hex, v: i32, out: &str, out_hex: &str| {
let v = u64::exact_from(v);
if T::convertible_from(v) {
test(s, s_hex, v, out, out_hex);
}
};
test_extreme(
"1.0",
"0x1.0#1",
Float::MAX_EXPONENT - 1,
"too_big",
"0x4.0E+268435455#1",
);
test_extreme(
"1.0",
"0x1.0#1",
Float::MAX_EXPONENT,
"Infinity",
"Infinity",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MAX_EXPONENT - 1,
"-too_big",
"-0x4.0E+268435455#1",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MAX_EXPONENT,
"-Infinity",
"-Infinity",
);
}
#[test]
fn test_shl_unsigned() {
test_shl_unsigned_helper::<u8, _>(|_, _, _| {});
test_shl_unsigned_helper::<u16, _>(|_, _, _| {});
test_shl_unsigned_helper::<u32, _>(|x, v, shifted| {
let mut n = rug::Float::exact_from(&x);
n <<= v;
assert_eq!(
ComparableFloatRef(&Float::from(&n)),
ComparableFloatRef(&shifted)
);
let n = rug::Float::exact_from(&x) << v;
assert_eq!(
ComparableFloatRef(&Float::from(&n)),
ComparableFloatRef(&shifted)
);
});
test_shl_unsigned_helper::<u64, _>(|_, _, _| {});
test_shl_unsigned_helper::<u128, _>(|_, _, _| {});
test_shl_unsigned_helper::<usize, _>(|_, _, _| {});
}
fn test_shl_signed_helper<T: PrimitiveSigned, F: Fn(Float, T, Float)>(f: F)
where
Float: ShlAssign<T> + Shl<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>,
{
let test = |s, s_hex, v: i64, out: &str, out_hex: &str| {
let x = parse_hex_string(s_hex);
assert_eq!(x.to_string(), s);
let v = T::exact_from(v);
let mut n = x.clone();
n <<= v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = x.clone() << v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = &x << v;
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
assert!(n.is_valid());
let n = shl_naive(x.clone(), v);
assert_eq!(n.to_string(), out);
assert_eq!(to_hex_string(&n), out_hex);
f(x, v, n);
};
test("NaN", "NaN", 0, "NaN", "NaN");
test("NaN", "NaN", 10, "NaN", "NaN");
test("NaN", "NaN", -10, "NaN", "NaN");
test("Infinity", "Infinity", 0, "Infinity", "Infinity");
test("Infinity", "Infinity", 10, "Infinity", "Infinity");
test("Infinity", "Infinity", -10, "Infinity", "Infinity");
test("-Infinity", "-Infinity", 0, "-Infinity", "-Infinity");
test("-Infinity", "-Infinity", 10, "-Infinity", "-Infinity");
test("-Infinity", "-Infinity", -10, "-Infinity", "-Infinity");
test("0.0", "0x0.0", 10, "0.0", "0x0.0");
test("0.0", "0x0.0", -10, "0.0", "0x0.0");
test("-0.0", "-0x0.0", 10, "-0.0", "-0x0.0");
test("-0.0", "-0x0.0", -10, "-0.0", "-0x0.0");
test("123.0", "0x7b.0#7", 0, "123.0", "0x7b.0#7");
test("123.0", "0x7b.0#7", 1, "246.0", "0xf6.0#7");
test("123.0", "0x7b.0#7", 10, "1.26e5", "0x1.ecE+4#7");
test("123.0", "0x7b.0#7", 100, "1.56e32", "0x7.bE+26#7");
test("123.0", "0x7b.0#7", -1, "61.5", "0x3d.8#7");
test("123.0", "0x7b.0#7", -10, "0.12", "0x0.1ec#7");
test("123.0", "0x7b.0#7", -100, "9.7e-29", "0x7.bE-24#7");
test("-123.0", "-0x7b.0#7", 0, "-123.0", "-0x7b.0#7");
test("-123.0", "-0x7b.0#7", 1, "-246.0", "-0xf6.0#7");
test("-123.0", "-0x7b.0#7", 10, "-1.26e5", "-0x1.ecE+4#7");
test("-123.0", "-0x7b.0#7", 100, "-1.56e32", "-0x7.bE+26#7");
test("-123.0", "-0x7b.0#7", -1, "-61.5", "-0x3d.8#7");
test("-123.0", "-0x7b.0#7", -10, "-0.12", "-0x0.1ec#7");
test("-123.0", "-0x7b.0#7", -100, "-9.7e-29", "-0x7.bE-24#7");
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
0,
"3.1415926535897931",
"0x3.243f6a8885a30#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
1,
"6.283185307179586",
"0x6.487ed5110b460#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
10,
"3216.9908772759482",
"0xc90.fdaa22168c0#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
100,
"3.9824418129956972e30",
"0x3.243f6a8885a30E+25#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
-1,
"1.5707963267948966",
"0x1.921fb54442d18#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
-10,
"0.0030679615757712823",
"0x0.00c90fdaa22168c0#53",
);
test(
"3.1415926535897931",
"0x3.243f6a8885a30#53",
-100,
"2.4782796245465248e-30",
"0x3.243f6a8885a30E-25#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
0,
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
1,
"-6.283185307179586",
"-0x6.487ed5110b460#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
10,
"-3216.9908772759482",
"-0xc90.fdaa22168c0#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
100,
"-3.9824418129956972e30",
"-0x3.243f6a8885a30E+25#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
-1,
"-1.5707963267948966",
"-0x1.921fb54442d18#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
-10,
"-0.0030679615757712823",
"-0x0.00c90fdaa22168c0#53",
);
test(
"-3.1415926535897931",
"-0x3.243f6a8885a30#53",
-100,
"-2.4782796245465248e-30",
"-0x3.243f6a8885a30E-25#53",
);
let test_extreme = |s, s_hex, v: i32, out: &str, out_hex: &str| {
let v = i64::from(v);
if T::convertible_from(v) {
test(s, s_hex, v, out, out_hex);
}
};
test_extreme(
"1.0",
"0x1.0#1",
Float::MAX_EXPONENT - 1,
"too_big",
"0x4.0E+268435455#1",
);
test_extreme(
"1.0",
"0x1.0#1",
Float::MAX_EXPONENT,
"Infinity",
"Infinity",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MAX_EXPONENT - 1,
"-too_big",
"-0x4.0E+268435455#1",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MAX_EXPONENT,
"-Infinity",
"-Infinity",
);
test_extreme(
"1.0",
"0x1.0#1",
Float::MIN_EXPONENT,
"too_small",
"0x2.0E-268435456#1",
);
test_extreme(
"1.0",
"0x1.0#1",
Float::MIN_EXPONENT - 1,
"too_small",
"0x1.0E-268435456#1",
);
test_extreme("1.0", "0x1.0#1", Float::MIN_EXPONENT - 2, "0.0", "0x0.0");
test_extreme(
"1.5",
"0x1.8#2",
Float::MIN_EXPONENT - 2,
"too_small",
"0x1.0E-268435456#2",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MIN_EXPONENT,
"-too_small",
"-0x2.0E-268435456#1",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MIN_EXPONENT - 1,
"-too_small",
"-0x1.0E-268435456#1",
);
test_extreme(
"-1.0",
"-0x1.0#1",
Float::MIN_EXPONENT - 2,
"-0.0",
"-0x0.0",
);
test_extreme(
"-1.5",
"-0x1.8#2",
Float::MIN_EXPONENT - 2,
"-too_small",
"-0x1.0E-268435456#2",
);
}
#[test]
fn test_shl_signed() {
test_shl_signed_helper::<i8, _>(|_, _, _| {});
test_shl_signed_helper::<i16, _>(|_, _, _| {});
test_shl_signed_helper::<i32, _>(|x, v, shifted| {
let mut n = rug::Float::exact_from(&x);
n <<= v;
assert_eq!(
ComparableFloatRef(&Float::from(&n)),
ComparableFloatRef(&shifted)
);
let n = rug::Float::exact_from(&x) << v;
assert_eq!(
ComparableFloatRef(&Float::from(&n)),
ComparableFloatRef(&shifted)
);
});
test_shl_signed_helper::<i64, _>(|_, _, _| {});
test_shl_signed_helper::<i128, _>(|_, _, _| {});
test_shl_signed_helper::<isize, _>(|_, _, _| {});
}
fn shl_properties_helper_unsigned_helper<T: PrimitiveUnsigned>(n: Float, u: T)
where
for<'a> &'a Integer: Shl<T, Output = Integer>,
Float: Shl<T, Output = Float>
+ ShlRound<T, Output = Float>
+ ShlAssign<T>
+ Shr<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>,
u64: TryFrom<T>,
i128: TryFrom<T>,
{
let mut mut_n = n.clone();
mut_n <<= u;
assert!(mut_n.is_valid());
let shifted = mut_n;
let shifted_alt = &n << u;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone() << u;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone().shl_round(u, Nearest).0;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone().shl_prec(u, n.get_prec().unwrap_or(1)).0;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
if i128::from(n.get_exponent().unwrap_or(1))
.wrapping_add(i128::exact_from(u))
.lt_abs(&1_000_000)
{
let shifted_alt = shl_naive(n.clone(), u);
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
}
if shifted.is_normal() {
assert_eq!(n.get_prec(), shifted.get_prec());
}
if !n.is_nan() {
assert!((&n << u).ge_abs(&n));
}
assert_eq!(ComparableFloat(-&n << u), ComparableFloat(-(&n << u)));
if shifted.is_normal() {
assert_eq!(ComparableFloatRef(&(&n << u >> u)), ComparableFloatRef(&n));
assert_eq!(
ComparableFloat(&n << u),
ComparableFloat(n * Float::power_of_2(u64::exact_from(u)))
);
}
}
fn shl_properties_helper_unsigned<T: PrimitiveUnsigned>()
where
for<'a> &'a Integer: Shl<T, Output = Integer>,
Float: Shl<T, Output = Float>
+ ShlRound<T, Output = Float>
+ ShlAssign<T>
+ Shr<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>,
u64: TryFrom<T>,
i128: TryFrom<T>,
{
float_unsigned_pair_gen_var_2::<T>().test_properties(|(n, u)| {
shl_properties_helper_unsigned_helper(n, u);
});
float_unsigned_pair_gen_var_3::<T>().test_properties(|(n, u)| {
shl_properties_helper_unsigned_helper(n, u);
});
float_gen().test_properties(|n| {
assert_eq!(ComparableFloat(&n << T::ZERO), ComparableFloat(n));
});
unsigned_gen::<T>().test_properties(|u| {
assert!((Float::NAN << u).is_nan());
assert_eq!(Float::INFINITY << u, Float::INFINITY);
assert_eq!(Float::NEGATIVE_INFINITY << u, Float::NEGATIVE_INFINITY);
assert_eq!(
ComparableFloat(Float::ZERO << u),
ComparableFloat(Float::ZERO)
);
assert_eq!(
ComparableFloat(Float::NEGATIVE_ZERO << u),
ComparableFloat(Float::NEGATIVE_ZERO)
);
});
unsigned_gen_var_5::<T>().test_properties(|u| {
assert!((Float::ONE << u).is_power_of_2());
});
integer_unsigned_pair_gen_var_2::<T>().test_properties(|(n, u)| {
assert_eq!(&n << u, Float::exact_from(n) << u);
});
}
#[allow(clippy::needless_pass_by_value)]
fn shl_properties_helper_signed_helper<T: PrimitiveSigned>(n: Float, i: T)
where
for<'a> &'a Integer: Shl<T, Output = Integer>,
Float: Shl<T, Output = Float>
+ ShlRound<T, Output = Float>
+ ShlAssign<T>
+ Shr<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>
+ Shl<<T as UnsignedAbs>::Output, Output = Float>
+ Shr<T, Output = Float>
+ Shr<<T as UnsignedAbs>::Output, Output = Float>,
i64: TryFrom<T>,
i128: TryFrom<T>,
{
let mut mut_n = n.clone();
mut_n <<= i;
assert!(mut_n.is_valid());
let shifted = mut_n;
let shifted_alt = &n << i;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone() << i;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone().shl_round(i, Nearest).0;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
let shifted_alt = n.clone().shl_prec(i, n.get_prec().unwrap_or(1)).0;
assert!(shifted_alt.is_valid());
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
if i128::from(n.get_exponent().unwrap_or(1))
.wrapping_add(i128::exact_from(i))
.lt_abs(&1_000_000)
{
let shifted_alt = shl_naive(n.clone(), i);
assert_eq!(
ComparableFloatRef(&shifted_alt),
ComparableFloatRef(&shifted)
);
}
if shifted.is_normal() {
assert_eq!(n.get_prec(), shifted.get_prec());
}
if i >= T::ZERO {
assert_eq!(
ComparableFloatRef(&(&n << i.unsigned_abs())),
ComparableFloatRef(&shifted)
);
} else if i != T::MIN {
assert_eq!(
ComparableFloatRef(&(&n >> i.unsigned_abs())),
ComparableFloatRef(&shifted)
);
}
assert_eq!(ComparableFloat(-&n << i), ComparableFloat(-(&n << i)));
if let Some(neg_i) = i.checked_neg() {
assert_eq!(ComparableFloat(&n << neg_i), ComparableFloat(&n >> i));
}
if shifted.is_normal() {
if shifted.get_exponent() != Some(Float::MIN_EXPONENT) {
assert_eq!(ComparableFloatRef(&(&n << i >> i)), ComparableFloatRef(&n));
}
assert_eq!(
ComparableFloat(shifted),
ComparableFloat(n * Float::power_of_2(i64::exact_from(i)))
);
}
}
fn shl_properties_helper_signed<T: PrimitiveSigned>()
where
for<'a> &'a Integer: Shl<T, Output = Integer>,
Float: Shl<T, Output = Float>
+ ShlRound<T, Output = Float>
+ ShlAssign<T>
+ Shr<T, Output = Float>,
Rational: Shl<T, Output = Rational>,
for<'a> &'a Float: Shl<T, Output = Float>
+ Shl<<T as UnsignedAbs>::Output, Output = Float>
+ Shr<T, Output = Float>
+ Shr<<T as UnsignedAbs>::Output, Output = Float>,
i64: TryFrom<T>,
i128: TryFrom<T>,
{
float_signed_pair_gen_var_2::<T>().test_properties(|(n, i)| {
shl_properties_helper_signed_helper(n, i);
});
float_signed_pair_gen_var_3::<T>().test_properties(|(n, i)| {
shl_properties_helper_signed_helper(n, i);
});
float_gen().test_properties(|n| {
assert_eq!(ComparableFloat(&n << T::ZERO), ComparableFloat(n));
});
signed_gen::<T>().test_properties(|i| {
assert!((Float::NAN << i).is_nan());
assert_eq!(Float::INFINITY << i, Float::INFINITY);
assert_eq!(Float::NEGATIVE_INFINITY << i, Float::NEGATIVE_INFINITY);
assert_eq!(
ComparableFloat(Float::ZERO << i),
ComparableFloat(Float::ZERO)
);
assert_eq!(
ComparableFloat(Float::NEGATIVE_ZERO << i),
ComparableFloat(Float::NEGATIVE_ZERO)
);
});
signed_gen_var_5::<T>().test_properties(|i| {
assert!((Float::ONE << i).is_power_of_2());
});
}
#[test]
fn shl_properties() {
apply_fn_to_unsigneds!(shl_properties_helper_unsigned);
apply_fn_to_signeds!(shl_properties_helper_signed);
float_unsigned_pair_gen_var_2::<u32>().test_properties(|(n, u)| {
let shifted = &n << u;
let mut rug_n = rug::Float::exact_from(&n);
rug_n <<= u;
assert_eq!(
ComparableFloatRef(&Float::from(&rug_n)),
ComparableFloatRef(&shifted)
);
assert_eq!(
ComparableFloat(Float::from(&(rug::Float::exact_from(&n) << u))),
ComparableFloat(shifted)
);
});
float_signed_pair_gen_var_2::<i32>().test_properties(|(n, i)| {
let shifted = &n << i;
let mut rug_n = rug::Float::exact_from(&n);
rug_n <<= i;
assert_eq!(
ComparableFloatRef(&Float::from(&rug_n)),
ComparableFloatRef(&shifted)
);
assert_eq!(
ComparableFloat(Float::from(&(rug::Float::exact_from(&n) << i))),
ComparableFloat(shifted)
);
});
}