computation_types/
enumerate.rs

1use core::fmt;
2
3use crate::{
4    impl_core_ops, peano::One, Computation, ComputationFn, Function, Name, NamedArgs, Names,
5};
6
7#[derive(Clone, Copy, Debug)]
8pub struct Enumerate<A, F>
9where
10    Self: Computation,
11{
12    pub child: A,
13    pub f: Function<(Name, Name), F>,
14}
15
16impl<A, F> Computation for Enumerate<A, F>
17where
18    A: Computation<Dim = One>,
19    F: Computation,
20{
21    type Dim = F::Dim;
22    type Item = F::Item;
23}
24
25impl<A, F> ComputationFn for Enumerate<A, F>
26where
27    Self: Computation,
28    A: ComputationFn,
29    Enumerate<A::Filled, F>: Computation,
30{
31    type Filled = Enumerate<A::Filled, F>;
32
33    fn fill(self, named_args: NamedArgs) -> Self::Filled {
34        Enumerate {
35            child: self.child.fill(named_args),
36            f: self.f,
37        }
38    }
39
40    fn arg_names(&self) -> Names {
41        self.child.arg_names()
42    }
43}
44
45impl_core_ops!(Enumerate<A, F>);
46
47impl<A, F> fmt::Display for Enumerate<A, F>
48where
49    Self: Computation,
50    A: fmt::Display,
51    F: fmt::Display,
52{
53    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
54        write!(f, "{}.enumerate({})", self.child, self.f.body)
55    }
56}
57
58#[cfg(test)]
59mod tests {
60    use proptest::prelude::*;
61    use test_strategy::proptest;
62
63    use crate::{arg1, val1, Computation, Function};
64
65    #[proptest]
66    fn enumerate_should_display(xs: Vec<usize>) {
67        let inp = val1!(xs.iter().cloned());
68        let f = Function::anonymous(("x", "i"), arg1!("x", usize) + arg1!("i", usize));
69        prop_assert_eq!(
70            inp.clone().enumerate(f).to_string(),
71            format!("{}.enumerate({})", inp, f.body)
72        );
73    }
74}