Skip to main content

Finite

Struct Finite 

Source
pub struct Finite<T: FiniteFloat>(/* private fields */);
Expand description

Experimental: A transparent wrapper around f64 and friends with total ordering.

Comparison, equality, and hashing all agree with total_cmp after zero normalization.

§Basic Usage

use range_set_blaze::{RangeSetBlaze, FiniteF64, FiniteF32};
let set = RangeSetBlaze::from_iter([FiniteF64::new(3.0)..=FiniteF64::new(5.0)]);
assert!(set.contains(FiniteF64::new(3.1)));
assert!(!set.contains(FiniteF64::new(2.9)));

let set = RangeSetBlaze::from(FiniteF64::from_primitive_range(3.0..=5.0));
assert!(set.contains(FiniteF64::new(4.9)));
assert!(!set.contains(FiniteF64::new(5.1)));

let set = RangeSetBlaze::from_iter(FiniteF32::from_primitive_ranges([3.0..=5.0, 7.0..=9.0]));
assert!(set.contains(FiniteF32::new(4.0)));
assert!(!set.contains(FiniteF32::new(6.0)));

§Enabling

This type is experimental and must be enabled with the float_experimental feature.

cargo add range-set-blaze --features "float_experimental"

That provides the FiniteF32 and FiniteF64 types.

If you’re building with nightly, you can instead use the float_nightly_experimental feature.

cargo add range-set-blaze --features "float_nightly_experimental"

To also use the FiniteF16 and FiniteF128 types.

Implementations§

Source§

impl<T: FiniteFloat> Finite<T>

Source

pub const MIN: Self

The minimum value that can be represented by the type.
Maps directly to crate::Integer::min_value()

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::MIN, FiniteF64::new(f64::MIN));
Source

pub const MAX: Self

The maximum value that can be represented by the type.
Maps directly to crate::Integer::max_value()

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::MAX, FiniteF64::new(f64::MAX));
Source

pub const MAX_SIZE: T::SafeLen = T::MAX_SIZE

The maximum possible size of a range, i.e. the size if [MIN..=MAX] For Finite types, this is unusual because NaN and infinity values are excluded, and -0.0 and +0.0 share one slot after normalization.

§Examples
use range_set_blaze::FiniteF32;

assert_eq!(FiniteF32::MAX_SIZE, 0xFF00_0000_u32 - 1);
Source

pub fn new(x: T) -> Self

Creates a new Finite from a primitive float. Only finite values are legal

§Examples
use range_set_blaze::FiniteF64;

let _ = FiniteF64::new(1.0);
§Panics

Panics if x.is_finite() returns false

Source

pub fn try_new(x: T) -> Option<Self>

Creates a new Finite from a primitive float.

Returns None if the float is not finite (NaN or infinity).

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::try_new(1.0), Some(FiniteF64::new(1.0)));
assert_eq!(FiniteF64::try_new(f64::NAN), None);
Source

pub const unsafe fn new_unchecked(x: T) -> Self

Creates a new Finite from a primitive float without validating it.

This is the unchecked building block every validating constructor in this module (new, try_new, from_primitive_range, values, from_primitive_slice, …) is defined in terms of. Prefer those; only reach for this when you have already independently established the safety precondition below and need to skip the redundant check.

§Safety

The caller must guarantee that:

  • x is finite: not NaN, not +/-infinity.
  • x is not -0.0: zero must already be canonicalized to +0.0.

Finite has a public type invariant (“only finite values, with zero canonicalized to +0.0, are legal”). Even though today’s implementation would only produce incorrect results (wrong MAX_SIZE, a duplicated zero slot, after/before landing somewhere unexpected) rather than immediate undefined behavior if this precondition is violated, safe code must never be able to construct a value that breaks it. This preserves the option for this crate, and downstream code, to rely on the invariant in future (potentially unsafe) abstractions without an audit of every safe caller.

Source

pub fn inclusive_end_from_start(self, b: T::SafeLen) -> Self

Computes self + (b - 1) where b is of type SafeLen.

§Panics

Panics if b is not small enough that the result stays within range for T (checked unconditionally, in both debug and release builds, so safe code can never construct a Finite value that breaks its invariant this way).

Source

pub fn start_from_inclusive_end(self, b: T::SafeLen) -> Self

Computes self - (b - 1) where b is of type SafeLen.

§Panics

Panics if b is not small enough that the result stays within range for T (checked unconditionally, in both debug and release builds, so safe code can never construct a Finite value that breaks its invariant this way).

Source

pub const fn into_inner(self) -> T

Returns the wrapped value.

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::new(42.0).into_inner(), 42.0);
Source

pub fn after(self) -> Self

Returns the next float, in total order.

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::new(42.0).after().before().into_inner(), 42.0);
§Panics

Panics if self is the maximum value (checked unconditionally, in both debug and release builds, so safe code can never construct a Finite value that breaks its invariant this way).

Source

pub fn before(self) -> Self

Returns the previous float, in total order.

§Examples
use range_set_blaze::FiniteF64;

assert_eq!(FiniteF64::new(42.0).before().after().into_inner(), 42.0);
§Panics

Panics if self is the minimum value (checked unconditionally, in both debug and release builds, so safe code can never construct a Finite value that breaks its invariant this way).

Source

pub fn checked_after(self) -> Option<Self>

Returns the next float, in total order.

Returns None if self is the maximum value.

§Examples
use range_set_blaze::FiniteF64;

let value = FiniteF64::new(42.0);
assert_eq!(value.checked_after(), Some(value.after()));
let value = FiniteF64::MAX;
assert_eq!(value.checked_after(), None);
Source

pub fn checked_before(self) -> Option<Self>

Returns the previous float, in total order.

Returns None if self is the minimum value.

§Examples
use range_set_blaze::FiniteF64;

let value = FiniteF64::new(42.0);
assert_eq!(value.checked_before(), Some(value.before()));
let value = FiniteF64::MIN;
assert_eq!(value.checked_before(), None);
Source

pub fn from_primitive_range(range: RangeInclusive<T>) -> RangeInclusive<Self>

Converts an inclusive primitive range into an inclusive Finite range.

“Primitive” here means Rust’s built-in float type (e.g. f64).

§Examples
use range_set_blaze::{RangeSetBlaze, FiniteF64};

let short = RangeSetBlaze::from(FiniteF64::from_primitive_range(3.0..=5.0));
let long = RangeSetBlaze::from(FiniteF64::new(3.0)..=FiniteF64::new(5.0));
assert_eq!(short, long);
§Panics

Panics if start or end is not finite.

Source

pub fn from_primitive_ranges<I>( ranges: I, ) -> impl Iterator<Item = RangeInclusive<Self>>
where I: IntoIterator<Item = RangeInclusive<T>>,

Converts inclusive primitive ranges into inclusive Finite ranges.

“Primitive” here means Rust’s built-in float type (e.g. f64).

§Examples
use range_set_blaze::{RangeSetBlaze, FiniteF64};

let short = RangeSetBlaze::from_iter(FiniteF64::from_primitive_ranges([1.0..=2.0, 3.0..=4.0]));
let long = RangeSetBlaze::from_iter([FiniteF64::new(1.0)..=FiniteF64::new(2.0), FiniteF64::new(3.0)..=FiniteF64::new(4.0)]);
assert_eq!(short, long);
§Panics

Panics when the returned iterator is consumed if any range endpoint is not finite.

Source

pub fn values<I>(values: I) -> impl Iterator<Item = Self>
where I: IntoIterator<Item = T>,

Convenience method to convert primitive values into ordered Finite values.

§Examples
use range_set_blaze::{RangeSetBlaze, FiniteF64};

let short = RangeSetBlaze::from_iter(FiniteF64::values([1.0, 2.0, 3.0, 4.0]));
let long = RangeSetBlaze::from_iter([FiniteF64::new(1.0), FiniteF64::new(2.0), FiniteF64::new(3.0), FiniteF64::new(4.0)]);
assert_eq!(short, long);
§Panics

Panics (when iterated) if any value is not finite.

Source

pub fn from_primitive_slice(values: &[T]) -> &[Self]

Views primitive values as ordered Finite values, validating as it goes.

“Primitive” here means Rust’s built-in float type (e.g. f64).

This runs in O(n) (to validate every element) and does not allocate.

§Examples
use range_set_blaze::{RangeSetBlaze, FiniteF64};

let short = RangeSetBlaze::from_iter(FiniteF64::from_primitive_slice(&[1.0, 2.0, 3.0, 4.0]));
let long = RangeSetBlaze::from_iter([FiniteF64::new(1.0), FiniteF64::new(2.0), FiniteF64::new(3.0), FiniteF64::new(4.0)]);
assert_eq!(short, long);
§Panics

Panics if any element is not finite, or is -0.0 (which can’t be normalized to +0.0 without copying — see Finite::from_primitive_slice_unchecked if you need a true zero-copy view and can guarantee your data already satisfies Finite’s invariant).

Source

pub const unsafe fn from_primitive_slice_unchecked(values: &[T]) -> &[Self]

Views primitive values as ordered Finite values, without validating them.

“Primitive” here means Rust’s built-in float type (e.g. f64).

This runs in O(1) and does not allocate.

§Safety

The caller must guarantee that every element of values is finite (not NaN, not +/-infinity) and not -0.0 (zero must already be canonicalized to +0.0). Because the returned slice is a live view over the same memory (not a copy), there is no opportunity to normalize -0.0 even if the caller wanted to; the data must already be clean.

Finite has a public type invariant that safe code must never be able to break, even though violating it today would only produce incorrect results (see Finite::new_unchecked for the full rationale).

Trait Implementations§

Source§

impl<T: Clone + FiniteFloat> Clone for Finite<T>

Source§

fn clone(&self) -> Finite<T>

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<T: Copy + FiniteFloat> Copy for Finite<T>

Source§

impl<T: Debug + FiniteFloat> Debug for Finite<T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<T: Default + FiniteFloat> Default for Finite<T>

Source§

fn default() -> Finite<T>

Returns the “default value” for a type. Read more
Source§

impl<T: FiniteFloat> Eq for Finite<T>

Source§

impl<T: FiniteFloat> Hash for Finite<T>

Source§

fn hash<H: Hasher>(&self, state: &mut H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl<T: FiniteFloat> Integer for Finite<T>

Source§

type SafeLen = <T as FiniteFloat>::SafeLen

The type representing the safe length for a RangeSetBlaze. For example, the length of a RangeSetBlaze<u8> is u16 to handle ranges up to 256 elements. For larger types like u128, this is represented by a custom type UIntPlusOne<u128>. Read more
Source§

fn checked_add_one(self) -> Option<Self>

Attempts to add one to the current value, returning None if the operation would overflow.
Source§

fn add_one(self) -> Self

Adds one to the current value, panicking in debug mode if the operation overflows. Read more
Source§

fn sub_one(self) -> Self

Subtracts one from the current value, panicking in debug mode if the operation underflows. Read more
Source§

fn assign_sub_one(&mut self)

Subtracts one from the current value and assigns it back to self.
Source§

fn range_next(range: &mut RangeInclusive<Self>) -> Option<Self>

Advances the iterator for the given range by one step, returning the next value or None if the range is exhausted. Read more
Source§

fn range_next_back(range: &mut RangeInclusive<Self>) -> Option<Self>

Advances the iterator for the given range in reverse by one step, returning the previous value or None if the range is exhausted. Read more
Source§

fn min_value() -> Self

Returns the minimum value that can be represented by the type. Read more
Source§

fn max_value() -> Self

Returns the maximum value that can be represented by the type. Read more
Source§

fn from_slice(slice: impl AsRef<[Self]>) -> RangeSetBlaze<Self>

Creates a RangeSetBlaze from a slice, specific to the integer type.
Source§

fn safe_len(r: &RangeInclusive<Self>) -> Self::SafeLen

Calculates the length of a range without overflow. Read more
Source§

fn safe_len_to_f64_lossy(len: Self::SafeLen) -> f64

Converts Integer::SafeLen to f64, potentially losing precision for large values.
Source§

fn f64_to_safe_len_lossy(f: f64) -> Self::SafeLen

Converts a f64 to Integer::SafeLen using the formula f as Self::SafeLen. For large integer types, this will result in a loss of precision.
Source§

fn inclusive_end_from_start(self, b: Self::SafeLen) -> Self

Computes self + (b - 1) where b is of type Integer::SafeLen. Read more
Source§

fn start_from_inclusive_end(self, b: Self::SafeLen) -> Self

Computes self - (b - 1) where b is of type Integer::SafeLen. Read more
Source§

fn exhausted_range() -> RangeInclusive<Self>

Returns an exhausted range, which is a range that starts from the maximum value and ends at the minimum value. This results in an empty range. Read more
Source§

impl<T: FiniteFloat> Ord for Finite<T>

Source§

fn cmp(&self, other: &Self) -> Ordering

This method returns an Ordering between self and other. Read more
1.21.0 (const: unstable) · Source§

fn max(self, other: Self) -> Self
where Self: Sized,

Compares and returns the maximum of two values. Read more
1.21.0 (const: unstable) · Source§

fn min(self, other: Self) -> Self
where Self: Sized,

Compares and returns the minimum of two values. Read more
1.50.0 (const: unstable) · Source§

fn clamp(self, min: Self, max: Self) -> Self
where Self: Sized,

Restrict a value to a certain interval. Read more
Source§

impl<T: FiniteFloat> PartialEq for Finite<T>

Source§

fn eq(&self, other: &Self) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl<T: FiniteFloat> PartialOrd for Finite<T>

Source§

fn partial_cmp(&self, other: &Self) -> Option<Ordering>

This method returns an ordering between self and other values if one exists. Read more
1.0.0 (const: unstable) · Source§

fn lt(&self, other: &Rhs) -> bool

Tests less than (for self and other) and is used by the < operator. Read more
1.0.0 (const: unstable) · Source§

fn le(&self, other: &Rhs) -> bool

Tests less than or equal to (for self and other) and is used by the <= operator. Read more
1.0.0 (const: unstable) · Source§

fn gt(&self, other: &Rhs) -> bool

Tests greater than (for self and other) and is used by the > operator. Read more
1.0.0 (const: unstable) · Source§

fn ge(&self, other: &Rhs) -> bool

Tests greater than or equal to (for self and other) and is used by the >= operator. Read more

Auto Trait Implementations§

§

impl<T> Freeze for Finite<T>
where T: Freeze,

§

impl<T> RefUnwindSafe for Finite<T>
where T: RefUnwindSafe,

§

impl<T> Send for Finite<T>

§

impl<T> Sync for Finite<T>

§

impl<T> Unpin for Finite<T>
where T: Unpin,

§

impl<T> UnsafeUnpin for Finite<T>
where T: UnsafeUnpin,

§

impl<T> UnwindSafe for Finite<T>
where T: UnwindSafe,

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Read<Exclusive, BecauseExclusive> for T
where T: ?Sized,

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V