smartcore/linalg/basic/
vector.rs

1use std::fmt::{Debug, Display};
2use std::ops::Range;
3
4use crate::linalg::basic::arrays::{Array, Array1, ArrayView1, MutArray, MutArrayView1};
5
6/// Provide mutable window on array
7#[derive(Debug)]
8pub struct VecMutView<'a, T: Debug + Display + Copy + Sized> {
9    ptr: &'a mut [T],
10}
11
12/// Provide window on array
13#[derive(Debug, Clone)]
14pub struct VecView<'a, T: Debug + Display + Copy + Sized> {
15    ptr: &'a [T],
16}
17
18impl<T: Debug + Display + Copy + Sized> Array<T, usize> for &[T] {
19    fn get(&self, i: usize) -> &T {
20        &self[i]
21    }
22
23    fn shape(&self) -> usize {
24        self.len()
25    }
26
27    fn is_empty(&self) -> bool {
28        self.len() > 0
29    }
30
31    fn iterator<'b>(&'b self, axis: u8) -> Box<dyn Iterator<Item = &'b T> + 'b> {
32        assert!(axis == 0, "For one dimensional array `axis` should == 0");
33        Box::new(self.iter())
34    }
35}
36
37impl<T: Debug + Display + Copy + Sized> Array<T, usize> for Vec<T> {
38    fn get(&self, i: usize) -> &T {
39        &self[i]
40    }
41
42    fn shape(&self) -> usize {
43        self.len()
44    }
45
46    fn is_empty(&self) -> bool {
47        self.len() > 0
48    }
49
50    fn iterator<'b>(&'b self, axis: u8) -> Box<dyn Iterator<Item = &'b T> + 'b> {
51        assert!(axis == 0, "For one dimensional array `axis` should == 0");
52        Box::new(self.iter())
53    }
54}
55
56impl<T: Debug + Display + Copy + Sized> MutArray<T, usize> for Vec<T> {
57    fn set(&mut self, i: usize, x: T) {
58        // NOTE: this panics in case of out of bounds index
59        self[i] = x
60    }
61
62    fn iterator_mut<'b>(&'b mut self, axis: u8) -> Box<dyn Iterator<Item = &'b mut T> + 'b> {
63        assert!(axis == 0, "For one dimensional array `axis` should == 0");
64        Box::new(self.iter_mut())
65    }
66}
67
68impl<T: Debug + Display + Copy + Sized> ArrayView1<T> for Vec<T> {}
69impl<T: Debug + Display + Copy + Sized> ArrayView1<T> for &[T] {}
70
71impl<T: Debug + Display + Copy + Sized> MutArrayView1<T> for Vec<T> {}
72
73impl<T: Debug + Display + Copy + Sized> Array1<T> for Vec<T> {
74    fn slice<'a>(&'a self, range: Range<usize>) -> Box<dyn ArrayView1<T> + 'a> {
75        assert!(
76            range.end <= self.len(),
77            "`range` should be <= {}",
78            self.len()
79        );
80        let view = VecView { ptr: &self[range] };
81        Box::new(view)
82    }
83
84    fn slice_mut<'b>(&'b mut self, range: Range<usize>) -> Box<dyn MutArrayView1<T> + 'b> {
85        assert!(
86            range.end <= self.len(),
87            "`range` should be <= {}",
88            self.len()
89        );
90        let view = VecMutView {
91            ptr: &mut self[range],
92        };
93        Box::new(view)
94    }
95
96    fn fill(len: usize, value: T) -> Self {
97        vec![value; len]
98    }
99
100    fn from_iterator<I: Iterator<Item = T>>(iter: I, len: usize) -> Self
101    where
102        Self: Sized,
103    {
104        let mut v: Vec<T> = Vec::with_capacity(len);
105        iter.take(len).for_each(|i| v.push(i));
106        v
107    }
108
109    fn from_vec_slice(slice: &[T]) -> Self {
110        let mut v: Vec<T> = Vec::with_capacity(slice.len());
111        slice.iter().for_each(|i| v.push(*i));
112        v
113    }
114
115    fn from_slice(slice: &dyn ArrayView1<T>) -> Self {
116        let mut v: Vec<T> = Vec::with_capacity(slice.shape());
117        slice.iterator(0).for_each(|i| v.push(*i));
118        v
119    }
120}
121
122impl<T: Debug + Display + Copy + Sized> Array<T, usize> for VecMutView<'_, T> {
123    fn get(&self, i: usize) -> &T {
124        &self.ptr[i]
125    }
126
127    fn shape(&self) -> usize {
128        self.ptr.len()
129    }
130
131    fn is_empty(&self) -> bool {
132        self.ptr.len() > 0
133    }
134
135    fn iterator<'b>(&'b self, axis: u8) -> Box<dyn Iterator<Item = &'b T> + 'b> {
136        assert!(axis == 0, "For one dimensional array `axis` should == 0");
137        Box::new(self.ptr.iter())
138    }
139}
140
141impl<T: Debug + Display + Copy + Sized> MutArray<T, usize> for VecMutView<'_, T> {
142    fn set(&mut self, i: usize, x: T) {
143        self.ptr[i] = x;
144    }
145
146    fn iterator_mut<'b>(&'b mut self, axis: u8) -> Box<dyn Iterator<Item = &'b mut T> + 'b> {
147        assert!(axis == 0, "For one dimensional array `axis` should == 0");
148        Box::new(self.ptr.iter_mut())
149    }
150}
151
152impl<T: Debug + Display + Copy + Sized> ArrayView1<T> for VecMutView<'_, T> {}
153impl<T: Debug + Display + Copy + Sized> MutArrayView1<T> for VecMutView<'_, T> {}
154
155impl<T: Debug + Display + Copy + Sized> Array<T, usize> for VecView<'_, T> {
156    fn get(&self, i: usize) -> &T {
157        &self.ptr[i]
158    }
159
160    fn shape(&self) -> usize {
161        self.ptr.len()
162    }
163
164    fn is_empty(&self) -> bool {
165        self.ptr.len() > 0
166    }
167
168    fn iterator<'b>(&'b self, axis: u8) -> Box<dyn Iterator<Item = &'b T> + 'b> {
169        assert!(axis == 0, "For one dimensional array `axis` should == 0");
170        Box::new(self.ptr.iter())
171    }
172}
173
174impl<T: Debug + Display + Copy + Sized> ArrayView1<T> for VecView<'_, T> {}
175
176#[cfg(test)]
177mod tests {
178    use super::*;
179    use crate::numbers::basenum::Number;
180
181    fn dot_product<T: Number, V: Array1<T>>(v: &V) -> T {
182        let vv = V::zeros(10);
183        let v_s = vv.slice(0..3);
184
185        v_s.dot(v)
186    }
187
188    fn vector_ops<T: Number + PartialOrd, V: Array1<T>>(_: &V) -> T {
189        let v = V::zeros(10);
190        v.max()
191    }
192
193    #[test]
194    fn test_get_set() {
195        let mut x = vec![1, 2, 3];
196        assert_eq!(3, *x.get(2));
197        x.set(1, 1);
198        assert_eq!(1, *x.get(1));
199    }
200
201    #[test]
202    #[should_panic]
203    fn test_failed_set() {
204        vec![1, 2, 3].set(3, 1);
205    }
206
207    #[test]
208    #[should_panic]
209    fn test_failed_get() {
210        vec![1, 2, 3].get(3);
211    }
212
213    #[test]
214    fn test_len() {
215        let x = [1, 2, 3];
216        assert_eq!(3, x.len());
217    }
218
219    #[test]
220    fn test_is_empty() {
221        assert!(vec![1; 0].is_empty());
222        assert!(!vec![1, 2, 3].is_empty());
223    }
224
225    #[test]
226    fn test_iterator() {
227        let v: Vec<i32> = vec![1, 2, 3].iterator(0).map(|&v| v * 2).collect();
228        assert_eq!(vec![2, 4, 6], v);
229    }
230
231    #[test]
232    #[should_panic]
233    fn test_failed_iterator() {
234        let _ = vec![1, 2, 3].iterator(1);
235    }
236
237    #[test]
238    fn test_mut_iterator() {
239        let mut x = vec![1, 2, 3];
240        x.iterator_mut(0).for_each(|v| *v *= 2);
241        assert_eq!(vec![2, 4, 6], x);
242    }
243
244    #[test]
245    #[should_panic]
246    fn test_failed_mut_iterator() {
247        let _ = vec![1, 2, 3].iterator_mut(1);
248    }
249
250    #[test]
251    fn test_slice() {
252        let x = vec![1, 2, 3, 4, 5];
253        let x_slice = x.slice(2..3);
254        assert_eq!(1, x_slice.shape());
255        assert_eq!(3, *x_slice.get(0));
256    }
257
258    #[test]
259    #[should_panic]
260    fn test_failed_slice() {
261        vec![1, 2, 3].slice(0..4);
262    }
263
264    #[test]
265    fn test_mut_slice() {
266        let mut x = vec![1, 2, 3, 4, 5];
267        let mut x_slice = x.slice_mut(2..4);
268        x_slice.set(0, 9);
269        assert_eq!(2, x_slice.shape());
270        assert_eq!(9, *x_slice.get(0));
271        assert_eq!(4, *x_slice.get(1));
272    }
273
274    #[test]
275    #[should_panic]
276    fn test_failed_mut_slice() {
277        vec![1, 2, 3].slice_mut(0..4);
278    }
279
280    #[test]
281    fn test_init() {
282        assert_eq!(Vec::fill(3, 0), vec![0, 0, 0]);
283        assert_eq!(
284            Vec::from_iterator([0, 1, 2, 3].iter().cloned(), 3),
285            vec![0, 1, 2]
286        );
287        assert_eq!(Vec::from_vec_slice(&[0, 1, 2]), vec![0, 1, 2]);
288        assert_eq!(Vec::from_vec_slice(&[0, 1, 2, 3, 4][2..]), vec![2, 3, 4]);
289        assert_eq!(Vec::from_slice(&vec![1, 2, 3, 4, 5]), vec![1, 2, 3, 4, 5]);
290        assert_eq!(
291            Vec::from_slice(vec![1, 2, 3, 4, 5].slice(0..3).as_ref()),
292            vec![1, 2, 3]
293        );
294    }
295
296    #[test]
297    fn test_mul_scalar() {
298        let mut x = vec![1., 2., 3.];
299
300        let mut y = Vec::<f32>::zeros(10);
301
302        y.slice_mut(0..2).add_scalar_mut(1.0);
303        y.sub_scalar(1.0);
304        x.slice_mut(0..2).sub_scalar_mut(2.);
305
306        assert_eq!(vec![-1.0, 0.0, 3.0], x);
307    }
308
309    #[test]
310    fn test_dot() {
311        let y_i = vec![1, 2, 3];
312        let y = vec![1.0, 2.0, 3.0];
313
314        println!("Regular dot1: {:?}", dot_product(&y));
315
316        let x = vec![4.0, 5.0, 6.0];
317        assert_eq!(32.0, y.slice(0..3).dot(&(*x.slice(0..3))));
318        assert_eq!(32.0, y.slice(0..3).dot(&x));
319        assert_eq!(32.0, y.dot(&x));
320        assert_eq!(14, y_i.dot(&y_i));
321    }
322
323    #[test]
324    fn test_operators() {
325        let mut x: Vec<f32> = Vec::zeros(10);
326
327        x.add_scalar(15.0);
328        {
329            let mut x_s = x.slice_mut(0..5);
330            x_s.add_scalar_mut(1.0);
331            assert_eq!(
332                vec![1.0, 1.0, 1.0, 1.0, 1.0],
333                x_s.iterator(0).copied().collect::<Vec<f32>>()
334            );
335        }
336
337        assert_eq!(1.0, x.slice(2..3).min());
338
339        assert_eq!(vec![1.0, 1.0, 1.0, 1.0, 1.0, 0.0, 0.0, 0.0, 0.0, 0.0], x);
340    }
341
342    #[test]
343    fn test_vector_ops() {
344        let x = vec![1., 2., 3.];
345
346        vector_ops(&x);
347    }
348}