use core::{convert::Infallible, num::NonZeroUsize};
use crate::{
DoubleEndedFallibleLender, DoubleEndedLender, ExactSizeFallibleLender, ExactSizeLender,
FallibleLend, FallibleLender, FallibleLending, FusedFallibleLender, FusedLender, Lender,
Lending,
};
#[derive(Clone, Debug)]
#[repr(transparent)]
#[must_use = "lenders are lazy and do nothing unless consumed"]
pub struct IntoFallible<L> {
pub(crate) lender: L,
}
impl<L: crate::Lender> IntoFallible<L> {
#[inline(always)]
pub(crate) fn new(lender: L) -> Self {
let _ = L::__check_covariance(crate::CovariantProof::new());
Self { lender }
}
#[inline(always)]
pub fn into_inner(self) -> L {
self.lender
}
}
impl<'lend, L> FallibleLending<'lend> for IntoFallible<L>
where
L: Lending<'lend>,
{
type Lend = L::Lend;
}
impl<L> FallibleLender for IntoFallible<L>
where
L: Lender,
{
type Error = Infallible;
crate::unsafe_assume_covariance_fallible!();
#[inline]
fn next(&mut self) -> Result<Option<FallibleLend<'_, Self>>, Self::Error> {
Ok(self.lender.next())
}
#[inline(always)]
fn size_hint(&self) -> (usize, Option<usize>) {
self.lender.size_hint()
}
#[inline]
fn nth(&mut self, n: usize) -> Result<Option<FallibleLend<'_, Self>>, Self::Error> {
Ok(self.lender.nth(n))
}
#[inline]
fn count(self) -> Result<usize, Self::Error>
where
Self: Sized,
{
Ok(self.lender.count())
}
#[inline]
fn last(&mut self) -> Result<Option<FallibleLend<'_, Self>>, Self::Error>
where
Self: Sized,
{
Ok(self.lender.last())
}
#[inline]
fn advance_by(&mut self, n: usize) -> Result<Result<(), NonZeroUsize>, Self::Error> {
Ok(self.lender.advance_by(n))
}
#[inline]
fn fold<B, F>(self, init: B, mut f: F) -> Result<B, Self::Error>
where
Self: Sized,
F: FnMut(B, FallibleLend<'_, Self>) -> Result<B, Self::Error>,
{
Ok(self.lender.fold(init, |acc, value| match f(acc, value) {
Ok(b) => b,
Err(e) => match e {},
}))
}
#[inline]
fn try_fold<B, F, R>(&mut self, init: B, mut f: F) -> Result<R, Self::Error>
where
F: FnMut(B, FallibleLend<'_, Self>) -> Result<R, Self::Error>,
R: stable_try_trait_v2::Try<Output = B>,
{
Ok(self.lender.try_fold(init, |acc, value| {
match f(acc, value) {
Ok(r) => r,
Err(e) => match e {},
}
}))
}
}
impl<L: Lender> From<L> for IntoFallible<L> {
#[inline(always)]
fn from(lender: L) -> Self {
Self::new(lender)
}
}
impl<L> DoubleEndedFallibleLender for IntoFallible<L>
where
L: DoubleEndedLender,
{
#[inline]
fn next_back(&mut self) -> Result<Option<FallibleLend<'_, Self>>, Self::Error> {
Ok(self.lender.next_back())
}
#[inline]
fn nth_back(&mut self, n: usize) -> Result<Option<FallibleLend<'_, Self>>, Self::Error> {
Ok(self.lender.nth_back(n))
}
#[inline]
fn advance_back_by(&mut self, n: usize) -> Result<Result<(), NonZeroUsize>, Self::Error> {
Ok(self.lender.advance_back_by(n))
}
#[inline]
fn rfold<B, F>(self, init: B, mut f: F) -> Result<B, Self::Error>
where
Self: Sized,
F: FnMut(B, FallibleLend<'_, Self>) -> Result<B, Self::Error>,
{
Ok(self.lender.rfold(init, |acc, value| match f(acc, value) {
Ok(b) => b,
Err(e) => match e {},
}))
}
#[inline]
fn try_rfold<B, F, R>(&mut self, init: B, mut f: F) -> Result<R, Self::Error>
where
F: FnMut(B, FallibleLend<'_, Self>) -> Result<R, Self::Error>,
R: stable_try_trait_v2::Try<Output = B>,
{
Ok(self
.lender
.try_rfold(init, |acc, value| match f(acc, value) {
Ok(r) => r,
Err(e) => match e {},
}))
}
}
impl<L> ExactSizeFallibleLender for IntoFallible<L>
where
L: ExactSizeLender,
{
#[inline(always)]
fn len(&self) -> usize {
self.lender.len()
}
#[inline(always)]
fn is_empty(&self) -> bool {
self.lender.is_empty()
}
}
impl<L> FusedFallibleLender for IntoFallible<L> where L: FusedLender {}