pub enum Validated<T, E> {
Good(T),
Fail(NEVec<E>),
}
Expand description
Similar to Result
, but cumulative in its error type.
§Error weaving
Consider that when using collect
in a “Traversable” way to pull a single
Result
out of an Iterator
containing many Result
s, it will fail on the
first Err
and short-circuit the iteration. This is suboptimal if we wish
to be made aware of every failure that (would have) occurred.
use validated::Validated::{self, Good, Fail};
use nonempty_collections::*;
let v = vec![Ok(1), Ok(2), Ok(3)];
let r: Validated<Vec<u32>, &str> = Good(vec![1, 2, 3]);
assert_eq!(r, v.into_iter().collect());
let v = vec![Ok(1), Err("Oh!"), Ok(2), Err("No!"), Ok(3)];
let r: Validated<Vec<u32>, &str> = Fail(nev!["Oh!", "No!"]);
assert_eq!(r, v.into_iter().collect());
Naturally iterators of Validated
values can be collected in a similar way:
use validated::Validated::{self, Good, Fail};
use nonempty_collections::*;
let v = vec![Good(1), Good(2), Good(3)];
let r: Validated<Vec<u32>, &str> = Good(vec![1, 2, 3]);
assert_eq!(r, v.into_iter().collect());
let v = vec![Good(1), Validated::fail("No!"), Good(3), Validated::fail("Ack!")];
let r: Validated<Vec<u32>, &str> = Fail(nev!["No!", "Ack!"]);
assert_eq!(r, v.into_iter().collect());
§Mapping composite results
This type also provides mapN
methods, which are surprisingly missing on
Option
and Result
.
use validated::Validated::{self, Good, Fail};
let v: Validated<u32, &str> = Good(1).map3(Good(2), Good(3), |a, b, c| a + b + c);
assert_eq!(v, Good(6));
For Validated
in particular these are quite useful, as a meaningful
and_then
cannot be written for it.
Formally, Validated
is not a Monad, but it is an Applicative Functor.
Variants§
Good(T)
Analogous to Result::Ok
.
Fail(NEVec<E>)
Analogous to Result::Err
, except that the error type is cumulative.
Implementations§
source§impl<T, E> Validated<T, E>
impl<T, E> Validated<T, E>
sourcepub fn as_mut(&mut self) -> Validated<&mut T, &mut E>
pub fn as_mut(&mut self) -> Validated<&mut T, &mut E>
Converts from &mut Validated<T, E>
to Validated<&mut T, &mut E>
.
Note: In the case of Fail
, a new Vec
of references is
allocated.
sourcepub fn as_ref(&self) -> Validated<&T, &E>
pub fn as_ref(&self) -> Validated<&T, &E>
Converts from &Validated<T, E>
to Validated<&T, &E>
.
Produces a new Validated
, containing references to the original,
leaving the original in place.
Note: In the case of Fail
, a new Vec
of references is
allocated.
sourcepub fn iter(&self) -> Iter<'_, T> ⓘ
pub fn iter(&self) -> Iter<'_, T> ⓘ
Returns an iterator over the possibly contained value.
The iterator yields one value if the result is Good
, otherwise
nothing.
sourcepub fn iter_mut(&mut self) -> IterMut<'_, T> ⓘ
pub fn iter_mut(&mut self) -> IterMut<'_, T> ⓘ
Returns a mutable iterator over the possibly contained value.
The iterator yields one value if the result is Good
, otherwise
nothing.
sourcepub fn map<U, F>(self, op: F) -> Validated<U, E>where
F: FnOnce(T) -> U,
pub fn map<U, F>(self, op: F) -> Validated<U, E>where
F: FnOnce(T) -> U,
Applies a function to the T
value of a Good
variant, or leaves
a Fail
variant untouched.
use validated::Validated::{self, Good, Fail};
let v: Validated<u32, &str> = Good(1);
let r = v.map(|n| n * 2);
assert_eq!(r, Good(2));
let v: Validated<u32, &str> = Validated::fail("No!");
let r = v.map(|n| n * 2);
assert_eq!(r, Validated::fail("No!"));
sourcepub fn map2<U, Z, F>(self, vu: Validated<U, E>, f: F) -> Validated<Z, E>where
F: FnOnce(T, U) -> Z,
pub fn map2<U, Z, F>(self, vu: Validated<U, E>, f: F) -> Validated<Z, E>where
F: FnOnce(T, U) -> Z,
Maps a function over two Validated
, but only if both are of the
Good
variant. If both failed, then their errors are concatenated.
use validated::Validated::{self, Good, Fail};
let v: Validated<u32, &str> = Good(1).map2(Good(2), |a, b| a + b);
assert_eq!(v, Good(3));
let v: Validated<u32, &str> = Good(1).map2(Validated::fail("No!"), |a, b: u32| a + b);
assert_eq!(v, Validated::fail("No!"));
sourcepub fn map3<U, V, Z, F>(
self,
vu: Validated<U, E>,
vv: Validated<V, E>,
f: F
) -> Validated<Z, E>where
F: FnOnce(T, U, V) -> Z,
pub fn map3<U, V, Z, F>(
self,
vu: Validated<U, E>,
vv: Validated<V, E>,
f: F
) -> Validated<Z, E>where
F: FnOnce(T, U, V) -> Z,
Maps a function over three Validated
, but only if all three are of the
Good
variant. If any failed, then their errors are concatenated.
use validated::Validated::{self, Good, Fail};
let v: Validated<u32, &str> = Good(1).map3(Good(2), Good(3), |a, b, c| a + b + c);
assert_eq!(v, Good(6));
let v: Validated<u32, &str> = Good(1).map3(Good(2), Validated::fail("No!"), |a, b, c: u32| a + b + c);
assert_eq!(v, Validated::fail("No!"));
sourcepub fn map4<U, V, W, Z, F>(
self,
vu: Validated<U, E>,
vv: Validated<V, E>,
vw: Validated<W, E>,
f: F
) -> Validated<Z, E>where
F: FnOnce(T, U, V, W) -> Z,
pub fn map4<U, V, W, Z, F>(
self,
vu: Validated<U, E>,
vv: Validated<V, E>,
vw: Validated<W, E>,
f: F
) -> Validated<Z, E>where
F: FnOnce(T, U, V, W) -> Z,
Maps a function over four Validated
, but only if all four are of the
Good
variant. If any failed, then their errors are concatenated.
sourcepub fn unwrap_or(self, default: T) -> T
pub fn unwrap_or(self, default: T) -> T
Returns the contained Good
value or a provided default.
Arguments passed to unwrap_or
are eagerly evaluated; if you are
passing the result of a function call, it is recommended to use
Validated::unwrap_or_else
instead.
§Examples
use validated::Validated;
let v: Validated<u32, &str> = Validated::Good(1);
assert_eq!(v.unwrap_or(2), 1);
let v: Validated<u32, &str> = Validated::fail("Oh no!");
assert_eq!(v.unwrap_or(2), 2);
sourcepub fn unwrap_or_else<F>(self, op: F) -> T
pub fn unwrap_or_else<F>(self, op: F) -> T
Returns the contained Good
value or computes it from a closure.
source§impl<T: Default, E> Validated<T, E>
impl<T: Default, E> Validated<T, E>
sourcepub fn unwrap_or_default(self) -> T
pub fn unwrap_or_default(self) -> T
Returns the contained Good
value or the default for T
.
source§impl<T: DerefMut, E> Validated<T, E>
impl<T: DerefMut, E> Validated<T, E>
sourcepub fn as_deref_mut(&mut self) -> Validated<&mut T::Target, &mut E>
pub fn as_deref_mut(&mut self) -> Validated<&mut T::Target, &mut E>
Like Result::as_deref_mut
.
Trait Implementations§
source§impl<T, U, E> FromIterator<Result<T, E>> for Validated<U, E>where
U: FromIterator<T>,
impl<T, U, E> FromIterator<Result<T, E>> for Validated<U, E>where
U: FromIterator<T>,
source§impl<T, U, E> FromIterator<Validated<T, E>> for Validated<U, E>where
U: FromIterator<T>,
impl<T, U, E> FromIterator<Validated<T, E>> for Validated<U, E>where
U: FromIterator<T>,
source§impl<'a, T, E> IntoIterator for &'a Validated<T, E>
impl<'a, T, E> IntoIterator for &'a Validated<T, E>
source§impl<'a, T, E> IntoIterator for &'a mut Validated<T, E>
impl<'a, T, E> IntoIterator for &'a mut Validated<T, E>
source§impl<T, E> IntoIterator for Validated<T, E>
impl<T, E> IntoIterator for Validated<T, E>
source§impl<T: Ord, E: Ord> Ord for Validated<T, E>
impl<T: Ord, E: Ord> Ord for Validated<T, E>
1.21.0 · source§fn max(self, other: Self) -> Selfwhere
Self: Sized,
fn max(self, other: Self) -> Selfwhere
Self: Sized,
source§impl<T: PartialEq, E: PartialEq> PartialEq for Validated<T, E>
impl<T: PartialEq, E: PartialEq> PartialEq for Validated<T, E>
source§impl<T: PartialOrd, E: PartialOrd> PartialOrd for Validated<T, E>
impl<T: PartialOrd, E: PartialOrd> PartialOrd for Validated<T, E>
1.0.0 · source§fn le(&self, other: &Rhs) -> bool
fn le(&self, other: &Rhs) -> bool
self
and other
) and is used by the <=
operator. Read moresource§impl<T, U, E> Sum<Result<U, E>> for Validated<T, E>where
T: Sum<U>,
impl<T, U, E> Sum<Result<U, E>> for Validated<T, E>where
T: Sum<U>,
use validated::Validated;
let ns: Validated<u32, ()> = [Ok(1), Ok(2), Ok(3)].into_iter().sum();
assert_eq!(Validated::Good(6), ns);
impl<T: Eq, E: Eq> Eq for Validated<T, E>
impl<T, E> StructuralPartialEq for Validated<T, E>
Auto Trait Implementations§
impl<T, E> Freeze for Validated<T, E>
impl<T, E> RefUnwindSafe for Validated<T, E>where
T: RefUnwindSafe,
E: RefUnwindSafe,
impl<T, E> Send for Validated<T, E>
impl<T, E> Sync for Validated<T, E>
impl<T, E> Unpin for Validated<T, E>
impl<T, E> UnwindSafe for Validated<T, E>where
T: UnwindSafe,
E: UnwindSafe,
Blanket Implementations§
source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
source§impl<T> IntoIteratorExt for Twhere
T: IntoIterator,
impl<T> IntoIteratorExt for Twhere
T: IntoIterator,
source§fn try_into_nonempty_iter(self) -> Option<<T as IntoIteratorExt>::IntoIter>
fn try_into_nonempty_iter(self) -> Option<<T as IntoIteratorExt>::IntoIter>
Tries to convert self
into NonEmptyIterator
. Calls self.next()
once. If self
doesn’t return Some
upon the first call to next()
,
returns None
.
§type Item = <T as IntoIterator>::Item
type Item = <T as IntoIterator>::Item
§type IntoIter = Chain<Once<<T as IntoIteratorExt>::Item>, <T as IntoIterator>::IntoIter>
type IntoIter = Chain<Once<<T as IntoIteratorExt>::Item>, <T as IntoIterator>::IntoIter>
NonEmptyIterator
are we turning this into?