extend_map/
lib.rs

1//! Wrap an `impl Extend` to map or filter elements before extending.
2
3use std::marker::PhantomData;
4
5/// Wraps a type `Extender: Extend<ExtendElement>` and applies a mapping function before passing elements to the `Extender`.
6pub struct ExtendMap<
7    'extender,
8    InputElement,
9    ExtendElement,
10    Mapper: FnMut(InputElement) -> ExtendElement,
11    Extender: Extend<ExtendElement>,
12> {
13    extender: &'extender mut Extender,
14    mapper: Mapper,
15    phantom_data: PhantomData<(InputElement, ExtendElement)>,
16}
17
18/// Wraps a type `Extender: Extend<ExtendElement>` and applies a filter function before passing elements to the `Extender`.
19pub struct ExtendFilter<
20    'extender,
21    Element,
22    Filter: FnMut(&Element) -> bool,
23    Extender: Extend<Element>,
24> {
25    extender: &'extender mut Extender,
26    filter: Filter,
27    phantom_data: PhantomData<Element>,
28}
29
30impl<
31        'extender,
32        InputElement,
33        ExtendElement,
34        Mapper: FnMut(InputElement) -> ExtendElement,
35        Extender: Extend<ExtendElement>,
36    > ExtendMap<'extender, InputElement, ExtendElement, Mapper, Extender>
37{
38    pub fn new(extender: &'extender mut Extender, mapper: Mapper) -> Self {
39        Self {
40            extender,
41            mapper,
42            phantom_data: PhantomData,
43        }
44    }
45
46    pub fn into_inner(self) -> &'extender mut Extender {
47        self.extender
48    }
49}
50
51impl<'extender, Element, Filter: FnMut(&Element) -> bool, Extender: Extend<Element>>
52    ExtendFilter<'extender, Element, Filter, Extender>
53{
54    pub fn new(extender: &'extender mut Extender, filter: Filter) -> Self {
55        Self {
56            extender,
57            filter,
58            phantom_data: PhantomData,
59        }
60    }
61
62    pub fn into_inner(self) -> &'extender mut Extender {
63        self.extender
64    }
65}
66
67impl<
68        InputElement,
69        ExtendElement,
70        Mapper: FnMut(InputElement) -> ExtendElement,
71        Extender: Extend<ExtendElement>,
72    > Extend<InputElement> for ExtendMap<'_, InputElement, ExtendElement, Mapper, Extender>
73{
74    fn extend<T: IntoIterator<Item = InputElement>>(&mut self, iter: T) {
75        self.extender.extend(iter.into_iter().map(&mut self.mapper));
76    }
77}
78
79impl<Element, Filter: FnMut(&Element) -> bool, Extender: Extend<Element>> Extend<Element>
80    for ExtendFilter<'_, Element, Filter, Extender>
81{
82    fn extend<T: IntoIterator<Item = Element>>(&mut self, iter: T) {
83        self.extender
84            .extend(iter.into_iter().filter(&mut self.filter));
85    }
86}