unsaferef 0.1.0

An unsafe reference without explicit lifetime
Documentation
#![cfg(feature="alloc")]

use crate::UnsafeRef;

pub enum UnsafeCow<T: ?Sized + ToOwned> {
    Ref(UnsafeRef<T>),
    Own(<T as ToOwned>::Owned)
}

impl<T: ?Sized + ToOwned> UnsafeCow<T> {
    #[inline]
    pub fn to_mut(&mut self) -> &mut <T as ToOwned>::Owned {
        if let Self::Ref(r) = self {
            *self = Self::Own((&**r).to_owned())
        }
        let Self::Own(o) = self else {unreachable!()};
        o
    }
}

impl<T: ?Sized + ToOwned> Clone for UnsafeCow<T> {
    fn clone(&self) -> Self {
        match self {
            Self::Ref(r) => Self::Ref(*r),
            Self::Own(o) => Self::Own(std::borrow::Borrow::borrow(o).to_owned())
        }
    }
}

impl<T: ?Sized + ToOwned> std::ops::Deref for UnsafeCow<T> {
    type Target = T;

    #[inline(always)]
    fn deref(&self) -> &Self::Target {
        match self {
            Self::Ref(r) => &**r,
            Self::Own(o) => std::borrow::Borrow::borrow(o)
        }
    }
}

impl<T: ?Sized + ToOwned + std::hash::Hash> std::hash::Hash for UnsafeCow<T> {
    #[inline]
    fn hash<H: std::hash::Hasher>(&self, state: &mut H) {
        (&**self).hash(state);
    }
}

impl<T: ?Sized + ToOwned + std::fmt::Debug> std::fmt::Debug for UnsafeCow<T> {
    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
        std::fmt::Debug::fmt(&**self, f)
    }
}
impl<T: ?Sized + ToOwned + std::fmt::Display> std::fmt::Display for UnsafeCow<T> {
    #[inline]
    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
        std::fmt::Display::fmt(&**self, f)
    }
}

impl<T: ?Sized + ToOwned + PartialEq> PartialEq for UnsafeCow<T>
where
    <T as ToOwned>::Owned: PartialEq
{
    fn eq(&self, other: &Self) -> bool {
        match (self, other) {
            (Self::Ref(r1), Self::Ref(r2)) => r1 == r2,
            (Self::Own(o1), Self::Own(o2)) => o1 == o2,
            _ => false
        }
    }
}
impl<T: ?Sized + ToOwned + PartialEq> PartialEq<T> for UnsafeCow<T>
where
    <T as ToOwned>::Owned: PartialEq<T>
{
    fn eq(&self, other: &T) -> bool {
        match self {
            Self::Ref(r) => r == other,
            Self::Own(o) => o == other,
        }
    }
}
impl<'t, T: ?Sized + ToOwned + PartialEq> PartialEq<&'t T> for UnsafeCow<T>
where
    <T as ToOwned>::Owned: PartialEq<&'t T>
{
    fn eq(&self, other: &&'t T) -> bool {
        match self {
            Self::Ref(r) => r == other,
            Self::Own(o) => o == other,
        }
    }
}
impl<T: ?Sized + ToOwned + PartialEq> Eq for UnsafeCow<T>
where <T as ToOwned>::Owned: PartialEq {}