Expand description
Comprehensive type-safe system for mathematical intervals with generic scalar support.
This module provides a complete interval arithmetic system that supports all standard interval types
and operations while ensuring correctness through Rust’s type system and extensive validation.
The design is fully generic over any type implementing num_valid::RealScalar
, providing
unprecedented flexibility and safety.
§Generic Design with num_valid::RealScalar
All interval types are generic over any scalar type implementing num_valid::RealScalar
.
This enables the same interval algorithms to work seamlessly across different scalar types
with varying performance and safety characteristics.
§Supported Scalar Types
Scalar Type | Performance | Validation | Best For |
---|---|---|---|
f64 | ⚡⚡⚡ Maximum | ❌ None | Trusted input, absolute maximum speed |
RealNative64StrictFiniteInDebug | ⚡⚡⚡ Same as f64 | ✅ Debug only | Recommended for most applications |
RealNative64StrictFinite | ⚡⚡ Small overhead | ✅ Always | Safety-critical applications |
RealRugStrictFinite | ⚡ Precision-dependent | ✅ Always | Arbitrary precision needs (available from the num-valid crate when compiled with --features=rug ) |
§Benefits of Generic Design
- Write Once, Use Everywhere: Same algorithms work with any scalar type
- Zero-Cost Safety:
RealNative64StrictFiniteInDebug
gives f64 performance with debug validation - Safety by Choice: Use validated types to eliminate floating-point edge cases
- Precision by Demand: Switch from f64 to arbitrary precision without code changes
- Development Safety: Catch NaN/∞ errors during development without release performance penalty
§Architecture Overview
The module is built around a four-tier hierarchy:
-
Bound Types:
LowerBoundOpen
,LowerBoundClosed
,UpperBoundOpen
,UpperBoundClosed
- Strongly-typed representations of interval boundaries
- Prevent mixing of open and closed bounds incorrectly
- Include validation and comparison logic
-
Concrete Interval Types: All mathematical interval variants
IntervalClosed
:[a, b]
- both bounds finite and includedIntervalOpen
:(a, b)
- both bounds finite and excludedIntervalLowerClosedUpperOpen
:[a, b)
- left closed, right openIntervalLowerOpenUpperClosed
:(a, b]
- left open, right closedIntervalLowerClosedUpperUnbounded
:[a, +∞)
- bounded below, unbounded aboveIntervalLowerOpenUpperUnbounded
:(a, +∞)
- strict lower bound, unbounded aboveIntervalLowerUnboundedUpperClosed
:(-∞, b]
- unbounded below, bounded aboveIntervalLowerUnboundedUpperOpen
:(-∞, b)
- unbounded below, strict upper boundIntervalSingleton
:{a}
- single point intervals
-
Interval Categories: Enum wrappers grouping related interval types
IntervalFinitePositiveLength
: All bounded intervals with positive lengthIntervalInfiniteLength
: All unbounded intervals- Provide unified interfaces for similar intervals
-
Universal Interface:
Interval
enum andIntervalTrait
- Top-level abstraction for all interval types
- Enables fully generic interval programming
- Provides conversion and interop between all types
§Design Philosophy
§Type Safety First
- Impossible to create invalid intervals (e.g.,
[2., 1.]
) - Boundary types prevent confusion between open/closed bounds
- Compile-time guarantees about interval properties
§Zero-Cost Abstractions
- Newtypes have zero runtime cost
- Generic code specializes to concrete types
- Debug assertions provide safety without release overhead
§Mathematical Correctness
- Proper handling of boundary cases
- Consistent intersection and containment logic
- Support for both discrete and continuous domains
§Quick Start Guide
§Recommended Approach for Most Applications
use grid1d::intervals::*;
use num_valid::RealNative64StrictFiniteInDebug;
use try_create::TryNew;
// Define your optimal type alias
type Real = RealNative64StrictFiniteInDebug;
// This gives you f64 performance with debug-time safety
let interval = IntervalClosed::new(
Real::try_new(0.0).unwrap(),
Real::try_new(1.0).unwrap()
);
// All operations compile to the same optimized assembly as raw f64
assert_eq!(interval.length().as_ref(), &1.0);
assert!(interval.contains_point(&Real::try_new(0.5).unwrap()));
§Different Scalar Types for Different Needs
use grid1d::intervals::*;
use num_valid::{RealNative64StrictFiniteInDebug, RealNative64StrictFinite};
use try_create::TryNew;
// Raw f64 for absolute maximum performance (use with caution)
let raw_interval = IntervalClosed::new(0.0_f64, 1.0_f64);
// Performance-optimal with debug safety (recommended)
let optimal_interval = IntervalClosed::new(
RealNative64StrictFiniteInDebug::try_new(0.0).unwrap(),
RealNative64StrictFiniteInDebug::try_new(1.0).unwrap()
);
// Always validated for safety-critical applications
let safe_interval = IntervalClosed::new(
RealNative64StrictFinite::try_new(0.0).unwrap(),
RealNative64StrictFinite::try_new(1.0).unwrap()
);
// All have identical APIs and mathematical behavior
assert_eq!(raw_interval.length().as_ref(), &1.0);
assert_eq!(optimal_interval.length().as_ref(), &1.0);
assert_eq!(safe_interval.length().as_ref(), &1.0);
§Generic Programming
use grid1d::intervals::*;
use num_valid::RealScalar;
// This function works with ANY scalar type implementing RealScalar
fn analyze_interval<I, T>(interval: &I) -> String
where
I: IntervalTrait<RealType = T>,
T: RealScalar + std::fmt::Display,
{
if interval.contains_point(&T::zero()) {
format!("Contains zero")
} else {
format!("Does not contain zero")
}
}
// Works with any interval type and scalar type
let closed = IntervalClosed::new(-1.0, 1.0);
let open = IntervalOpen::new(0.0, 2.0);
let unbounded = IntervalLowerClosedUpperUnbounded::new(0.0);
assert_eq!(analyze_interval(&closed), "Contains zero");
assert_eq!(analyze_interval(&open), "Does not contain zero");
assert_eq!(analyze_interval(&unbounded), "Contains zero");
§Advanced Features
§Type Conversions
use grid1d::intervals::*;
let closed = IntervalClosed::new(0.0, 1.0);
let general: Interval<f64> = closed.into();
let back: IntervalClosed<f64> = general.try_into().unwrap();
§Intersection and Set Operations
use grid1d::intervals::*;
let a = IntervalClosed::new(0.0, 2.0); // [0, 2]
let b = IntervalClosed::new(1.0, 3.0); // [1, 3]
if let Some(intersection) = a.intersection(&b) {
// Result: [1, 2]
println!("Intersection: {:?}", intersection);
}
§Performance Notes
- All bound checks are compile-time in release builds
- Generic code specializes to zero-cost concrete operations
- Memory layout is optimal (single word for most interval types)
- No heap allocations in normal operation
§Error Handling
IntervalError
for unified error handling- Specific error types for different failure modes
- Backtrace support for debugging
- Both fallible (
try_new
) and panicking (new
) constructors
Structs§
- Interval
Bounded - Generic bounded interval structure for intervals with two finite endpoints.
- Interval
Lower Bounded Upper Unbounded - Generic structure for intervals bounded below and extending to positive infinity.
- Interval
Lower Unbounded Upper Bounded - FINAL DOC Generic structure for intervals extending from negative infinity with finite upper bound.
- Interval
Lower Unbounded Upper Unbounded - The universal unbounded interval
(-∞, +∞)
representing the entire real line. - Interval
Singleton - A singleton interval
[a]
containing exactly one point.
Enums§
- Errors
Interval Construction - Comprehensive error types for interval construction failures.
- Errors
Interval Conversion - FINAL DOC Comprehensive error handling for interval type conversion operations.
- Interval
- FINAL DOC Universal container for all interval types in the library.
- Interval
Finite Length - FINAL DOC Container for all intervals with finite, measurable length.
- Interval
Finite Positive Length - FINAL DOC Container for all intervals with finite, positive, measurable length.
- Interval
Infinite Length - FINAL DOC Container for all intervals with infinite, unbounded length.
- Interval
Union - Represents the union of intervals, which can be either connected or disjoint.
- SubInterval
InPartition - Enum containing the different types of intervals that defines a partition of an interval with positive (and finite) length.
Traits§
- Contains
- Core trait for point containment testing in mathematical intervals.
- HasLower
Bound - Common interface for intervals that have a finite lower bound.
- HasUpper
Bound - Common interface for intervals that have a finite upper bound.
- Interval
Finite Positive Length Trait - Common interface for intervals with finite, positive, measurable length.
- Interval
Lower Bounded Upper Unbounded Trait - Common interface for intervals with finite lower bounds extending to positive infinity.
- Interval
Lower Unbounded Upper Bounded Trait - Common interface for intervals extending from negative infinity with finite upper bounds.
- Interval
Operations - Common trait for intervals with operations between different interval types.
- Interval
Trait - Universal interface for all interval types providing common operations.
Type Aliases§
- Interval
Closed - FINAL DOC A closed interval
[a, b]
where both endpoints are included. - Interval
Lower Closed Upper Open - FINAL DOC A right half-open interval
[a, b)
where the lower endpoint is included and the upper endpoint is excluded. - Interval
Lower Closed Upper Unbounded - A lower closed, upper unbounded interval
[a, +∞)
where the lower endpoint is included and extends to positive infinity. - Interval
Lower Open Upper Closed - FINAL DOC A left half-open interval
(a, b]
where the lower endpoint is excluded and the upper endpoint is included. - Interval
Lower Open Upper Unbounded - An unbounded open-left interval
(a, +∞)
where the lower endpoint is excluded and extends to positive infinity. - Interval
Lower Unbounded Upper Closed - An upper bounded interval
(-∞, b]
extending from negative infinity with the upper endpoint included. - Interval
Lower Unbounded Upper Open - An unbounded open-right interval
(-∞, b)
extending from negative infinity with the upper endpoint excluded. - Interval
Open - FINAL DOC An open interval
(a, b)
where both endpoints are excluded.