use std::ops::Not;
use super::{
ALWAYS_FALSE_NAME,
ALWAYS_TRUE_NAME,
BoxPredicate,
Predicate,
Rc,
impl_predicate_clone,
impl_predicate_common_methods,
impl_predicate_debug_display,
impl_rc_conversions,
impl_shared_predicate_methods,
};
pub struct RcPredicate<T> {
pub(super) function: Rc<dyn Fn(&T) -> bool>,
pub(super) name: Option<String>,
}
impl<T> RcPredicate<T> {
impl_predicate_common_methods!(RcPredicate<T>, (Fn(&T) -> bool + 'static), |f| Rc::new(f));
impl_shared_predicate_methods!(RcPredicate<T>, 'static);
}
impl<T> Not for RcPredicate<T>
where
T: 'static,
{
type Output = RcPredicate<T>;
fn not(self) -> Self::Output {
let function = self.function;
RcPredicate::new(move |value| !function(value))
}
}
impl<T> Not for &RcPredicate<T>
where
T: 'static,
{
type Output = RcPredicate<T>;
fn not(self) -> Self::Output {
let function = self.function.clone();
RcPredicate::new(move |value| !function(value))
}
}
impl_predicate_clone!(RcPredicate<T>);
impl_predicate_debug_display!(RcPredicate<T>);
impl<T> Predicate<T> for RcPredicate<T> {
fn test(&self, value: &T) -> bool {
(self.function)(value)
}
impl_rc_conversions!(
RcPredicate<T>,
BoxPredicate,
Fn(t: &T) -> bool
);
}