use core::{
cmp, fmt,
ops::{Bound, RangeBounds},
};
use crate::{seal::Seal, Portable};
#[derive(Clone, Copy, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRangeFull;
impl fmt::Debug for ArchivedRangeFull {
#[inline]
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(fmt, "..")
}
}
#[derive(Clone, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRange<T> {
pub start: T,
pub end: T,
}
impl<T: fmt::Debug> fmt::Debug for ArchivedRange<T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
self.start.fmt(fmt)?;
write!(fmt, "..")?;
self.end.fmt(fmt)?;
Ok(())
}
}
impl<T: PartialOrd<T>> ArchivedRange<T> {
pub fn contains<U>(&self, item: &U) -> bool
where
T: PartialOrd<U>,
U: PartialOrd<T> + ?Sized,
{
<Self as RangeBounds<T>>::contains(self, item)
}
pub fn is_empty(&self) -> bool {
match self.start.partial_cmp(&self.end) {
None
| Some(cmp::Ordering::Greater)
| Some(cmp::Ordering::Equal) => true,
Some(cmp::Ordering::Less) => false,
}
}
}
impl<T> RangeBounds<T> for ArchivedRange<T> {
fn start_bound(&self) -> Bound<&T> {
Bound::Included(&self.start)
}
fn end_bound(&self) -> Bound<&T> {
Bound::Excluded(&self.end)
}
}
#[derive(Clone, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRangeInclusive<T> {
pub start: T,
pub end: T,
}
impl<T: fmt::Debug> fmt::Debug for ArchivedRangeInclusive<T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
self.start.fmt(fmt)?;
write!(fmt, "..=")?;
self.end.fmt(fmt)?;
Ok(())
}
}
impl<T: PartialOrd<T>> ArchivedRangeInclusive<T> {
pub fn contains<U>(&self, item: &U) -> bool
where
T: PartialOrd<U>,
U: PartialOrd<T> + ?Sized,
{
<Self as RangeBounds<T>>::contains(self, item)
}
pub fn is_empty(&self) -> bool {
match self.start.partial_cmp(&self.end) {
None | Some(cmp::Ordering::Greater) => true,
Some(cmp::Ordering::Less) | Some(cmp::Ordering::Equal) => false,
}
}
}
impl<T> RangeBounds<T> for ArchivedRangeInclusive<T> {
fn start_bound(&self) -> Bound<&T> {
Bound::Included(&self.start)
}
fn end_bound(&self) -> Bound<&T> {
Bound::Included(&self.end)
}
}
#[derive(Clone, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRangeFrom<T> {
pub start: T,
}
impl<T: fmt::Debug> fmt::Debug for ArchivedRangeFrom<T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
self.start.fmt(fmt)?;
write!(fmt, "..")?;
Ok(())
}
}
impl<T: PartialOrd<T>> ArchivedRangeFrom<T> {
pub fn contains<U>(&self, item: &U) -> bool
where
T: PartialOrd<U>,
U: ?Sized + PartialOrd<T>,
{
<Self as RangeBounds<T>>::contains(self, item)
}
}
impl<T> RangeBounds<T> for ArchivedRangeFrom<T> {
fn start_bound(&self) -> Bound<&T> {
Bound::Included(&self.start)
}
fn end_bound(&self) -> Bound<&T> {
Bound::Unbounded
}
}
#[derive(Clone, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRangeTo<T> {
pub end: T,
}
impl<T: fmt::Debug> fmt::Debug for ArchivedRangeTo<T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(fmt, "..")?;
self.end.fmt(fmt)?;
Ok(())
}
}
impl<T: PartialOrd<T>> ArchivedRangeTo<T> {
pub fn contains<U>(&self, item: &U) -> bool
where
T: PartialOrd<U>,
U: ?Sized + PartialOrd<T>,
{
<Self as RangeBounds<T>>::contains(self, item)
}
}
impl<T> RangeBounds<T> for ArchivedRangeTo<T> {
fn start_bound(&self) -> Bound<&T> {
Bound::Unbounded
}
fn end_bound(&self) -> Bound<&T> {
Bound::Excluded(&self.end)
}
}
#[derive(Clone, Default, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[rkyv(crate)]
#[repr(C)]
pub struct ArchivedRangeToInclusive<T> {
pub end: T,
}
impl<T: fmt::Debug> fmt::Debug for ArchivedRangeToInclusive<T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(fmt, "..=")?;
self.end.fmt(fmt)?;
Ok(())
}
}
impl<T: PartialOrd<T>> ArchivedRangeToInclusive<T> {
pub fn contains<U>(&self, item: &U) -> bool
where
T: PartialOrd<U>,
U: ?Sized + PartialOrd<T>,
{
<Self as RangeBounds<T>>::contains(self, item)
}
}
impl<T> RangeBounds<T> for ArchivedRangeToInclusive<T> {
fn start_bound(&self) -> Bound<&T> {
Bound::Unbounded
}
fn end_bound(&self) -> Bound<&T> {
Bound::Included(&self.end)
}
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, Portable)]
#[cfg_attr(feature = "bytecheck", derive(bytecheck::CheckBytes))]
#[repr(u8)]
#[rkyv(crate)]
pub enum ArchivedBound<T> {
Included(T),
Excluded(T),
Unbounded,
}
impl<T> ArchivedBound<T> {
pub fn as_ref(&self) -> Bound<&T> {
match self {
ArchivedBound::Included(x) => Bound::Included(x),
ArchivedBound::Excluded(x) => Bound::Excluded(x),
ArchivedBound::Unbounded => Bound::Unbounded,
}
}
pub fn as_mut(&mut self) -> Bound<&mut T> {
match self {
ArchivedBound::Included(x) => Bound::Included(x),
ArchivedBound::Excluded(x) => Bound::Excluded(x),
ArchivedBound::Unbounded => Bound::Unbounded,
}
}
pub fn as_seal(this: Seal<'_, Self>) -> Bound<Seal<'_, T>> {
let this = unsafe { Seal::unseal_unchecked(this) };
match this {
ArchivedBound::Included(x) => Bound::Included(Seal::new(x)),
ArchivedBound::Excluded(x) => Bound::Excluded(Seal::new(x)),
ArchivedBound::Unbounded => Bound::Unbounded,
}
}
}