Skip to main content

feanor_math/seq/
conversion.rs

1use std::marker::PhantomData;
2use std::num::NonZero;
3
4use super::*;
5
6/// Iterator over the elements of a [`VectorFn`].
7/// Produced by the function [`VectorFn::iter()`] and [`VectorFn::into_iter()`].
8#[derive(Debug)]
9pub struct VectorFnIter<V: VectorFn<T>, T> {
10    content: V,
11    begin: usize,
12    end: usize,
13    element: PhantomData<T>,
14}
15
16impl<V: VectorFn<T>, T> VectorFnIter<V, T> {
17    pub fn new(content: V) -> Self {
18        Self {
19            end: content.len(),
20            content,
21            begin: 0,
22            element: PhantomData,
23        }
24    }
25}
26
27impl<V: Clone + VectorFn<T>, T> Clone for VectorFnIter<V, T> {
28    fn clone(&self) -> Self {
29        Self {
30            begin: self.begin,
31            end: self.end,
32            content: self.content.clone(),
33            element: PhantomData,
34        }
35    }
36}
37
38impl<V: Copy + VectorFn<T>, T> Copy for VectorFnIter<V, T> {}
39
40impl<V: VectorFn<T>, T> Iterator for VectorFnIter<V, T> {
41    type Item = T;
42
43    fn next(&mut self) -> Option<Self::Item> {
44        if self.begin < self.end {
45            self.begin += 1;
46            return Some(self.content.at(self.begin - 1));
47        } else {
48            return None;
49        }
50    }
51
52    fn advance_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
53        if self.begin + n <= self.end {
54            self.begin += n;
55            return Ok(());
56        } else {
57            let lacking_elements = n - (self.end - self.begin);
58            self.begin = self.end;
59            return Err(NonZero::new(lacking_elements).unwrap());
60        }
61    }
62
63    fn size_hint(&self) -> (usize, Option<usize>) { (self.len(), Some(self.len())) }
64}
65
66impl<V: VectorFn<T>, T> DoubleEndedIterator for VectorFnIter<V, T> {
67    fn next_back(&mut self) -> Option<Self::Item> {
68        if self.begin < self.end {
69            self.end -= 1;
70            return Some(self.content.at(self.end));
71        } else {
72            return None;
73        }
74    }
75
76    fn advance_back_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
77        if self.begin + n <= self.end {
78            self.end -= n;
79            return Ok(());
80        } else {
81            let lacking_elements = n - (self.end - self.begin);
82            self.end = self.begin;
83            return Err(NonZero::new(lacking_elements).unwrap());
84        }
85    }
86}
87
88impl<V: VectorFn<T>, T> ExactSizeIterator for VectorFnIter<V, T> {
89    fn len(&self) -> usize { self.end - self.begin }
90}
91
92/// A [`VectorFn`] that produces its elements by cloning the elements of an underlying
93/// [`VectorView`]. Produced by the functions [`VectorView::clone_els()`] and
94/// [`VectorView::clone_ring_els()`].
95#[derive(Debug)]
96pub struct CloneElFn<V: VectorView<T>, T, F: Fn(&T) -> T> {
97    content: V,
98    clone_el: F,
99    element: PhantomData<T>,
100}
101
102impl<V: Clone + VectorView<T>, T, F: Clone + Fn(&T) -> T> Clone for CloneElFn<V, T, F> {
103    fn clone(&self) -> Self {
104        Self {
105            clone_el: self.clone_el.clone(),
106            content: self.content.clone(),
107            element: PhantomData,
108        }
109    }
110}
111
112impl<V: Copy + VectorView<T>, T, F: Copy + Fn(&T) -> T> Copy for CloneElFn<V, T, F> {}
113
114impl<V: VectorView<T>, T, F: Fn(&T) -> T> CloneElFn<V, T, F> {
115    /// Creates a new [`CloneElFn`].
116    ///
117    /// In most circumstances, it is easier to instead use the functions [`VectorView::clone_els()`]
118    /// and [`VectorView::clone_ring_els()`] to produce a [`CloneElFn`].
119    pub fn new(content: V, clone_el: F) -> Self {
120        Self {
121            content,
122            clone_el,
123            element: PhantomData,
124        }
125    }
126}
127
128impl<V: SelfSubvectorView<T>, T, F: Fn(&T) -> T> SelfSubvectorFn<T> for CloneElFn<V, T, F> {
129    fn restrict_full(self, range: Range<usize>) -> Self {
130        Self {
131            content: self.content.restrict_full(range),
132            clone_el: self.clone_el,
133            element: PhantomData,
134        }
135    }
136}
137
138impl<V: VectorView<T>, T, F: Fn(&T) -> T> VectorFn<T> for CloneElFn<V, T, F> {
139    fn at(&self, i: usize) -> T { (self.clone_el)(self.content.at(i)) }
140
141    fn len(&self) -> usize { self.content.len() }
142}
143
144/// Wrapper around [`VectorView`] that interprets it as a [`VectorFn`]. The elements it provides are
145/// just the same references that would be returned through [`VectorFn::at()`].
146/// Produced by the function [`VectorView::as_fn()`].
147#[derive(Debug)]
148pub struct VectorViewFn<'a, V: ?Sized + VectorView<T>, T: ?Sized> {
149    content: &'a V,
150    element: PhantomData<T>,
151}
152
153impl<'a, V: ?Sized + VectorView<T>, T: ?Sized> Clone for VectorViewFn<'a, V, T> {
154    fn clone(&self) -> Self { *self }
155}
156
157impl<'a, V: ?Sized + VectorView<T>, T: ?Sized> Copy for VectorViewFn<'a, V, T> {}
158
159impl<'a, V: ?Sized + VectorView<T>, T: ?Sized> VectorViewFn<'a, V, T> {
160    /// Creates a new [`VectorViewFn`].
161    /// In most circumstances, it is easier to instead use the function [`VectorView::as_fn()`].
162    pub fn new(content: &'a V) -> Self {
163        Self {
164            content,
165            element: PhantomData,
166        }
167    }
168}
169
170impl<'a, V: ?Sized + VectorView<T>, T: ?Sized> VectorFn<&'a T> for VectorViewFn<'a, V, T> {
171    fn at(&self, i: usize) -> &'a T { self.content.at(i) }
172
173    fn len(&self) -> usize { self.content.len() }
174}