easy_ml/matrices/
iterators.rs

1/*!
2 * Iterators over parts of a Matrix
3 *
4 * - Over a row: Row[(Reference)](RowReferenceIterator)[(Mut)](RowReferenceMutIterator)[Iterator](RowIterator)
5 * - Over a column: Column[(Reference)](ColumnReferenceIterator)[(Mut)](ColumnReferenceMutIterator)[Iterator](ColumnIterator)
6 * - Over all data in row major order: RowMajor[(Reference)](RowMajorReferenceIterator)[(Mut)](RowMajorReferenceMutIterator)[(Owned)](RowMajorOwnedIterator)[Iterator](RowMajorIterator)
7 * - Over all data in column major order: ColumnMajor[(Reference)](ColumnMajorReferenceIterator)[(Mut)](ColumnMajorReferenceMutIterator)[(Owned)](ColumnMajorOwnedIterator)[Iterator](ColumnMajorIterator)
8 * - Over the main diagonal: Diagonal[(Reference)](DiagonalReferenceIterator)[(Mut)](DiagonalReferenceMutIterator)[Iterator](DiagonalIterator)
9 *
10 * # Examples
11 *
12 * Extending a matrix with new columns
13 * ```
14 * use easy_ml::matrices::Matrix;
15 *
16 * // we start with some matrix where the first and second columns correspond
17 * // to x and y points
18 * let mut matrix = Matrix::from(vec![
19 *     vec![ 3.0, 4.0 ],
20 *     vec![ 8.0, 1.0 ],
21 *     vec![ 2.0, 9.0 ]]);
22 * // insert a third column based on the formula x * y
23 * matrix.insert_column_with(2, matrix.column_iter(0)
24 *     // join together the x and y columns
25 *     .zip(matrix.column_iter(1))
26 *     // compute the values for the new column
27 *     .map(|(x, y)| x * y)
28 *     // Collect into a vector so we stop immutably borrowing from `matrix`.
29 *     // This is only neccessary when we use the data from a Matrix to modify itself,
30 *     // because the rust compiler enforces that we do not mutably and immutably borrow
31 *     // something at the same time. If we used data from a different Matrix to update
32 *     // `matrix` then we could stop at map and pass the iterator directly.
33 *     .collect::<Vec<f64>>()
34 *     // now that the Vec created owns the data for the new column and we have stopped
35 *     // borrowing immutably from `matrix` we turn the vec back into an iterator and
36 *     // mutably borrow `matrix` to add the new column
37 *     .drain(..));
38 * assert_eq!(matrix.get(0, 2), 3.0 * 4.0);
39 * assert_eq!(matrix.get(1, 2), 8.0 * 1.0);
40 * assert_eq!(matrix.get(2, 2), 2.0 * 9.0);
41 * ```
42 *
43 * # Matrix layout and iterator performance
44 *
45 * Internally the Matrix type uses a flattened array with [row major storage](https://en.wikipedia.org/wiki/Row-_and_column-major_order)
46 * of the data. Due to [CPU cache lines](https://stackoverflow.com/questions/3928995/how-do-cache-lines-work)
47 * this means row major access of elements is likely to be faster than column major indexing,
48 * once a matrix is large enough, so you should favor iterating through each row.
49 *
50 * ```
51 * use easy_ml::matrices::Matrix;
52 * let matrix = Matrix::from(vec![
53 *    vec![ 1, 2 ],
54 *    vec![ 3, 4 ]]);
55 * // storage of elements is [1, 2, 3, 4]
56 *
57 * // row major access
58 * for row in 0..2 {
59 *     for column in 0..2 {
60 *         println!("{}", matrix.get(row, column));
61 *     }
62 * } // -> 1 2 3 4
63 * matrix.row_major_iter().for_each(|e| println!("{}", e)); // -> 1 2 3 4
64 * matrix.row_major_iter().with_index().for_each(|e| println!("{:?}", e)); // -> ((0, 0), 1) ((0, 1), 2), ((1, 0), 3), ((1, 1), 4)
65 *
66 * // column major access
67 * for column in 0..2 {
68 *     for row in 0..2 {
69 *         println!("{}", matrix.get(row, column));
70 *     }
71 * } // -> 1 3 2 4
72 * matrix.column_major_iter().for_each(|e| println!("{}", e)); // -> 1 3 2 4
73 * matrix.column_major_iter().with_index().for_each(|e| println!("{:?}", e)); // // -> ((0, 0), 1), ((1, 0), 3), ((0, 1), 2), ((1, 1), 4)
74 * ```
75 *
76 * Iterators are also able to elide array indexing bounds checks which may improve performance over
77 * explicit calls to get or get_reference in a loop, however you can use unsafe getters to elide
78 * bounds checks in loops as well so you are not forced to use iterators even if the checks are
79 * a performance concern.
80 */
81
82use std::iter::{ExactSizeIterator, FusedIterator};
83use std::marker::PhantomData;
84use std::ops::Range;
85
86use crate::matrices::views::{MatrixMut, MatrixRef, NoInteriorMutability};
87use crate::matrices::{Column, Matrix, Row};
88
89trait MatrixRefExtension<T>: MatrixRef<T> {
90    /**
91     * Helper for asserting starting indexes are in range.
92     */
93    fn index_is_valid(&self, row: Row, column: Column) -> bool {
94        row < self.view_rows() && column < self.view_columns()
95    }
96}
97
98impl<R, T> MatrixRefExtension<T> for R where R: MatrixRef<T> {}
99
100/**
101 * A wrapper around another iterator that iterates through each element in the iterator and
102 * includes the index used to access the element.
103 *
104 * This is like a 2D version of [`enumerate`](std::iter::Iterator::enumerate).
105 */
106#[derive(Debug)]
107pub struct WithIndex<I> {
108    pub(crate) iterator: I,
109}
110
111impl<I> WithIndex<I> {
112    /**
113     * Consumes the WithIndex, yielding the iterator it was created from.
114     */
115    pub fn source(self) -> I {
116        self.iterator
117    }
118}
119
120/**
121 * An iterator over a column in a matrix.
122 *
123 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
124 * ```ignore
125 * [
126 *   1, 2
127 *   3, 4
128 * ]
129 * ```
130 * Depending on the column iterator you want to obtain,
131 * can either iterate through 1, 3 or 2, 4.
132 */
133#[derive(Debug)]
134pub struct ColumnIterator<'a, T: Clone, S: MatrixRef<T> = Matrix<T>> {
135    matrix: &'a S,
136    column: Column,
137    range: Range<Row>,
138    _type: PhantomData<&'a T>,
139}
140
141impl<'a, T: Clone> ColumnIterator<'a, T> {
142    /**
143     * Constructs a column iterator over this matrix.
144     *
145     * # Panics
146     *
147     * Panics if the column does not exist in this matrix.
148     */
149    #[track_caller]
150    pub fn new(matrix: &Matrix<T>, column: Column) -> ColumnIterator<T> {
151        ColumnIterator::from(matrix, column)
152    }
153}
154
155impl<'a, T: Clone, S: MatrixRef<T>> ColumnIterator<'a, T, S> {
156    /**
157     * Constructs a column iterator over this source.
158     *
159     * # Panics
160     *
161     * Panics if the column does not exist in this source.
162     */
163    #[track_caller]
164    pub fn from(source: &S, column: Column) -> ColumnIterator<T, S> {
165        assert!(
166            source.index_is_valid(0, column),
167            "Expected ({},{}) to be in range",
168            0,
169            column
170        );
171        ColumnIterator {
172            matrix: source,
173            column,
174            range: 0..source.view_rows(),
175            _type: PhantomData,
176        }
177    }
178}
179
180impl<'a, T: Clone, S: MatrixRef<T>> Iterator for ColumnIterator<'a, T, S> {
181    type Item = T;
182
183    fn next(&mut self) -> Option<Self::Item> {
184        match self.range.next() {
185            None => None,
186            Some(row) => unsafe {
187                // Safety: We initialised the range to 0..matrix.view_rows(), and
188                // checked we can read from this column at creation, hence if
189                // the view_rows have not changed this read is in bounds and if
190                // they are able to be changed, then the MatrixRef implementation is
191                // required to bounds check for us.
192                Some(
193                    self.matrix
194                        .get_reference_unchecked(row, self.column)
195                        .clone(),
196                )
197            },
198        }
199    }
200
201    fn size_hint(&self) -> (usize, Option<usize>) {
202        self.range.size_hint()
203    }
204}
205impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for ColumnIterator<'a, T, S> {}
206impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for ColumnIterator<'a, T, S> {}
207
208/**
209 * An iterator over a row in a matrix.
210 *
211 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
212 * ```ignore
213 * [
214 *   1, 2
215 *   3, 4
216 * ]
217 * ```
218 * Depending on the row iterator you want to obtain,
219 * can either iterate through 1, 2 or 3, 4.
220 */
221#[derive(Debug)]
222pub struct RowIterator<'a, T: Clone, S: MatrixRef<T> = Matrix<T>> {
223    matrix: &'a S,
224    row: Row,
225    range: Range<Column>,
226    _type: PhantomData<&'a T>,
227}
228
229impl<'a, T: Clone> RowIterator<'a, T> {
230    /**
231     * Constructs a row iterator over this matrix.
232     *
233     * # Panics
234     *
235     * Panics if the row does not exist in this matrix.
236     */
237    #[track_caller]
238    pub fn new(matrix: &Matrix<T>, row: Row) -> RowIterator<T> {
239        RowIterator::from(matrix, row)
240    }
241}
242
243impl<'a, T: Clone, S: MatrixRef<T>> RowIterator<'a, T, S> {
244    /**
245     * Constructs a row iterator over this source.
246     *
247     * # Panics
248     *
249     * Panics if the row does not exist in this source.
250     */
251    #[track_caller]
252    pub fn from(source: &S, row: Row) -> RowIterator<T, S> {
253        assert!(
254            source.index_is_valid(row, 0),
255            "Expected ({},{}) to be in range",
256            row,
257            0
258        );
259        RowIterator {
260            matrix: source,
261            row,
262            range: 0..source.view_columns(),
263            _type: PhantomData,
264        }
265    }
266}
267
268impl<'a, T: Clone, S: MatrixRef<T>> Iterator for RowIterator<'a, T, S> {
269    type Item = T;
270
271    fn next(&mut self) -> Option<Self::Item> {
272        match self.range.next() {
273            None => None,
274            Some(column) => unsafe {
275                // Safety: We initialised the range to 0..matrix.view_columns(), and
276                // checked we can read from this row at creation, hence if
277                // the view_columns have not changed this read is in bounds and if
278                // they are able to be changed, then the MatrixRef implementation is
279                // required to bounds check for us.
280                Some(
281                    self.matrix
282                        .get_reference_unchecked(self.row, column)
283                        .clone(),
284                )
285            },
286        }
287    }
288
289    fn size_hint(&self) -> (usize, Option<usize>) {
290        self.range.size_hint()
291    }
292}
293impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for RowIterator<'a, T, S> {}
294impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for RowIterator<'a, T, S> {}
295
296// Common column major iterator logic
297fn column_major_iter(
298    finished: &mut bool,
299    rows: Row,
300    columns: Column,
301    row_counter: &mut Row,
302    column_counter: &mut Column,
303) -> Option<(Row, Column)> {
304    if *finished {
305        return None;
306    }
307
308    let value = Some((*row_counter, *column_counter));
309
310    if *row_counter == rows - 1 && *column_counter == columns - 1 {
311        // reached end of matrix for next iteration
312        *finished = true;
313    }
314
315    if *row_counter == rows - 1 {
316        // reached end of a column, need to reset to first element in next column
317        *row_counter = 0;
318        *column_counter += 1;
319    } else {
320        // keep incrementing through this column
321        *row_counter += 1;
322    }
323
324    value
325}
326
327// Common column major iterator size hint logic
328fn column_major_size_hint(
329    rows: Row,
330    columns: Column,
331    row_counter: Row,
332    column_counter: Column,
333) -> (usize, Option<usize>) {
334    let remaining_columns = columns - column_counter;
335    match remaining_columns {
336        0 => (0, Some(0)),
337        1 => {
338            // we're on the last column, so return how many items are left for us to
339            // go through with the row counter
340            let remaining_rows = rows - row_counter;
341            (remaining_rows, Some(remaining_rows))
342        }
343        x => {
344            // we still have at least one full column left in addition to what's left
345            // for this column's row counter
346            let remaining_rows = rows - row_counter;
347            // each full column takes as many iterations as the matrix has rows
348            let remaining_full_columns = (x - 1) * rows;
349            let remaining = remaining_rows + remaining_full_columns;
350            (remaining, Some(remaining))
351        }
352    }
353}
354
355/**
356 * A column major iterator over all values in a matrix.
357 *
358 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
359 * ```ignore
360 * [
361 *   1, 2
362 *   3, 4
363 * ]
364 * ```
365 * The elements will be iterated through as 1, 3, 2, 4
366 */
367#[derive(Debug)]
368pub struct ColumnMajorIterator<'a, T: Clone, S: MatrixRef<T> = Matrix<T>> {
369    matrix: &'a S,
370    column_counter: Column,
371    columns: Column,
372    row_counter: Row,
373    rows: Row,
374    finished: bool,
375    _type: PhantomData<&'a T>,
376}
377
378impl<'a, T: Clone> ColumnMajorIterator<'a, T> {
379    /**
380     * Constructs a column major iterator over this matrix.
381     */
382    pub fn new(matrix: &Matrix<T>) -> ColumnMajorIterator<T> {
383        ColumnMajorIterator::from(matrix)
384    }
385}
386
387impl<'a, T: Clone, S: MatrixRef<T>> ColumnMajorIterator<'a, T, S> {
388    /**
389     * Constructs a column major iterator over this source.
390     */
391    pub fn from(source: &S) -> ColumnMajorIterator<T, S> {
392        ColumnMajorIterator {
393            matrix: source,
394            column_counter: 0,
395            columns: source.view_columns(),
396            row_counter: 0,
397            rows: source.view_rows(),
398            finished: !source.index_is_valid(0, 0),
399            _type: PhantomData,
400        }
401    }
402
403    /**
404     * Constructs an iterator which also yields the row and column index of each element in
405     * this iterator.
406     */
407    pub fn with_index(self) -> WithIndex<Self> {
408        WithIndex { iterator: self }
409    }
410}
411
412impl<'a, T: Clone, S: MatrixRef<T>> From<ColumnMajorIterator<'a, T, S>>
413    for WithIndex<ColumnMajorIterator<'a, T, S>>
414{
415    fn from(iterator: ColumnMajorIterator<'a, T, S>) -> Self {
416        iterator.with_index()
417    }
418}
419
420impl<'a, T: Clone, S: MatrixRef<T>> Iterator for ColumnMajorIterator<'a, T, S> {
421    type Item = T;
422
423    fn next(&mut self) -> Option<Self::Item> {
424        column_major_iter(
425            &mut self.finished,
426            self.rows,
427            self.columns,
428            &mut self.row_counter,
429            &mut self.column_counter,
430        )
431        .map(|(row, column)| unsafe {
432            // Safety: We checked on creation that 0,0 is in range, and after getting
433            // our next value we check if we hit the end of the matrix and will avoid
434            // calling this on our next loop if we finished. Hence if the view size has
435            // not changed this read is in bounds and if they are able to be changed,
436            // then the MatrixRef implementation is required to bounds check for us.
437            self.matrix.get_reference_unchecked(row, column).clone()
438        })
439    }
440
441    fn size_hint(&self) -> (usize, Option<usize>) {
442        column_major_size_hint(
443            self.rows,
444            self.columns,
445            self.row_counter,
446            self.column_counter,
447        )
448    }
449}
450impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for ColumnMajorIterator<'a, T, S> {}
451impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for ColumnMajorIterator<'a, T, S> {}
452
453impl<'a, T: Clone, S: MatrixRef<T>> Iterator for WithIndex<ColumnMajorIterator<'a, T, S>> {
454    type Item = ((Row, Column), T);
455
456    fn next(&mut self) -> Option<Self::Item> {
457        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
458        self.iterator.next().map(|x| ((row, column), x))
459    }
460
461    fn size_hint(&self) -> (usize, Option<usize>) {
462        self.iterator.size_hint()
463    }
464}
465impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for WithIndex<ColumnMajorIterator<'a, T, S>> {}
466/**
467 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
468 * did not return an exact size
469 */
470impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for WithIndex<ColumnMajorIterator<'a, T, S>> {}
471
472// Common row major iterator logic
473fn row_major_iter(
474    finished: &mut bool,
475    rows: Row,
476    columns: Column,
477    row_counter: &mut Row,
478    column_counter: &mut Column,
479) -> Option<(Row, Column)> {
480    if *finished {
481        return None;
482    }
483
484    let value = Some((*row_counter, *column_counter));
485
486    if *column_counter == columns - 1 && *row_counter == rows - 1 {
487        // reached end of matrix for next iteration
488        *finished = true;
489    }
490
491    if *column_counter == columns - 1 {
492        // reached end of a row, need to reset to first element in next row
493        *column_counter = 0;
494        *row_counter += 1;
495    } else {
496        // keep incrementing through this row
497        *column_counter += 1;
498    }
499
500    value
501}
502
503// Common row major iterator size hint logic
504fn row_major_size_hint(
505    rows: Row,
506    columns: Column,
507    row_counter: Row,
508    column_counter: Column,
509) -> (usize, Option<usize>) {
510    let remaining_rows = rows - row_counter;
511    match remaining_rows {
512        0 => (0, Some(0)),
513        1 => {
514            // we're on the last row, so return how many items are left for us to
515            // go through with the column counter
516            let remaining_columns = columns - column_counter;
517            (remaining_columns, Some(remaining_columns))
518        }
519        x => {
520            // we still have at least one full row left in addition to what's left
521            // for this row's column counter
522            let remaining_columns = columns - column_counter;
523            // each full row takes as many iterations as the matrix has columns
524            let remaining_full_rows = (x - 1) * columns;
525            let remaining = remaining_columns + remaining_full_rows;
526            (remaining, Some(remaining))
527        }
528    }
529}
530
531/**
532 * A row major iterator over all values in a matrix.
533 *
534 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
535 * ```ignore
536 * [
537 *   1, 2
538 *   3, 4
539 * ]
540 * ```
541 * The elements will be iterated through as 1, 2, 3, 4
542 */
543#[derive(Debug)]
544pub struct RowMajorIterator<'a, T: Clone, S: MatrixRef<T> = Matrix<T>> {
545    matrix: &'a S,
546    column_counter: Column,
547    columns: Column,
548    row_counter: Row,
549    rows: Row,
550    finished: bool,
551    _type: PhantomData<&'a T>,
552}
553
554impl<'a, T: Clone> RowMajorIterator<'a, T> {
555    /**
556     * Constructs a row major iterator over this matrix.
557     */
558    pub fn new(matrix: &Matrix<T>) -> RowMajorIterator<T> {
559        RowMajorIterator::from(matrix)
560    }
561}
562
563impl<'a, T: Clone, S: MatrixRef<T>> RowMajorIterator<'a, T, S> {
564    /**
565     * Constructs a row major iterator over this source.
566     */
567    pub fn from(source: &S) -> RowMajorIterator<T, S> {
568        RowMajorIterator {
569            matrix: source,
570            column_counter: 0,
571            columns: source.view_columns(),
572            row_counter: 0,
573            rows: source.view_rows(),
574            finished: !source.index_is_valid(0, 0),
575            _type: PhantomData,
576        }
577    }
578
579    /**
580     * Constructs an iterator which also yields the row and column index of each element in
581     * this iterator.
582     */
583    pub fn with_index(self) -> WithIndex<Self> {
584        WithIndex { iterator: self }
585    }
586}
587
588impl<'a, T: Clone, S: MatrixRef<T>> From<RowMajorIterator<'a, T, S>>
589    for WithIndex<RowMajorIterator<'a, T, S>>
590{
591    fn from(iterator: RowMajorIterator<'a, T, S>) -> Self {
592        iterator.with_index()
593    }
594}
595
596impl<'a, T: Clone, S: MatrixRef<T>> Iterator for RowMajorIterator<'a, T, S> {
597    type Item = T;
598
599    fn next(&mut self) -> Option<Self::Item> {
600        row_major_iter(
601            &mut self.finished,
602            self.rows,
603            self.columns,
604            &mut self.row_counter,
605            &mut self.column_counter,
606        )
607        .map(|(row, column)| unsafe {
608            // Safety: We checked on creation that 0,0 is in range, and after getting
609            // our next value we check if we hit the end of the matrix and will avoid
610            // calling this on our next loop if we finished. Hence if the view size has
611            // not changed this read is in bounds and if they are able to be changed,
612            // then the MatrixRef implementation is required to bounds check for us.
613            self.matrix.get_reference_unchecked(row, column).clone()
614        })
615    }
616
617    fn size_hint(&self) -> (usize, Option<usize>) {
618        row_major_size_hint(
619            self.rows,
620            self.columns,
621            self.row_counter,
622            self.column_counter,
623        )
624    }
625}
626impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for RowMajorIterator<'a, T, S> {}
627impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for RowMajorIterator<'a, T, S> {}
628
629impl<'a, T: Clone, S: MatrixRef<T>> Iterator for WithIndex<RowMajorIterator<'a, T, S>> {
630    type Item = ((Row, Column), T);
631
632    fn next(&mut self) -> Option<Self::Item> {
633        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
634        self.iterator.next().map(|x| ((row, column), x))
635    }
636
637    fn size_hint(&self) -> (usize, Option<usize>) {
638        self.iterator.size_hint()
639    }
640}
641impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for WithIndex<RowMajorIterator<'a, T, S>> {}
642/**
643 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
644 * did not return an exact size
645 */
646impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for WithIndex<RowMajorIterator<'a, T, S>> {}
647
648/**
649 * An iterator over references to a column in a matrix.
650 *
651 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
652 * ```ignore
653 * [
654 *   1, 2
655 *   3, 4
656 * ]
657 * ```
658 * Depending on the row iterator you want to obtain,
659 * can either iterate through &1, &3 or &2, &4.
660 */
661#[derive(Debug)]
662pub struct ColumnReferenceIterator<'a, T, S: MatrixRef<T> = Matrix<T>> {
663    matrix: &'a S,
664    column: Column,
665    range: Range<Row>,
666    _type: PhantomData<&'a T>,
667}
668
669impl<'a, T> ColumnReferenceIterator<'a, T> {
670    /**
671     * Constructs a column iterator over this matrix.
672     *
673     * # Panics
674     *
675     * Panics if the column does not exist in this matrix.
676     */
677    #[track_caller]
678    pub fn new(matrix: &Matrix<T>, column: Column) -> ColumnReferenceIterator<T> {
679        ColumnReferenceIterator::from(matrix, column)
680    }
681}
682
683impl<'a, T, S: MatrixRef<T>> ColumnReferenceIterator<'a, T, S> {
684    /**
685     * Constructs a column iterator over this source.
686     *
687     * # Panics
688     *
689     * Panics if the column does not exist in this source.
690     */
691    #[track_caller]
692    pub fn from(source: &S, column: Column) -> ColumnReferenceIterator<T, S> {
693        assert!(
694            source.index_is_valid(0, column),
695            "Expected ({},{}) to be in range",
696            0,
697            column
698        );
699        ColumnReferenceIterator {
700            matrix: source,
701            column,
702            range: 0..source.view_rows(),
703            _type: PhantomData,
704        }
705    }
706}
707
708impl<'a, T, S: MatrixRef<T>> Iterator for ColumnReferenceIterator<'a, T, S> {
709    type Item = &'a T;
710
711    fn next(&mut self) -> Option<Self::Item> {
712        match self.range.next() {
713            None => None,
714            Some(row) => unsafe {
715                // Safety: We initialised the range to 0..matrix.view_rows(), and
716                // checked we can read from this column at creation, hence if
717                // the view_rows have not changed this read is in bounds and if
718                // they are able to be changed, then the MatrixRef implementation is
719                // required to bounds check for us.
720                Some(self.matrix.get_reference_unchecked(row, self.column))
721            },
722        }
723    }
724
725    fn size_hint(&self) -> (usize, Option<usize>) {
726        self.range.size_hint()
727    }
728}
729impl<'a, T, S: MatrixRef<T>> FusedIterator for ColumnReferenceIterator<'a, T, S> {}
730impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for ColumnReferenceIterator<'a, T, S> {}
731
732/**
733 * An iterator over references to a row in a matrix.
734 *
735 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
736 * ```ignore
737 * [
738 *   1, 2
739 *   3, 4
740 * ]
741 * ```
742 * Depending on the row iterator you want to obtain,
743 * can either iterate through &1, &2 or &3, &4.
744 */
745#[derive(Debug)]
746pub struct RowReferenceIterator<'a, T, S: MatrixRef<T> = Matrix<T>> {
747    matrix: &'a S,
748    row: Row,
749    range: Range<Column>,
750    _type: PhantomData<&'a T>,
751}
752
753impl<'a, T> RowReferenceIterator<'a, T> {
754    /**
755     * Constructs a row iterator over this matrix.
756     *
757     * # Panics
758     *
759     * Panics if the row does not exist in this matrix.
760     */
761    #[track_caller]
762    pub fn new(matrix: &Matrix<T>, row: Row) -> RowReferenceIterator<T> {
763        RowReferenceIterator::from(matrix, row)
764    }
765}
766
767impl<'a, T, S: MatrixRef<T>> RowReferenceIterator<'a, T, S> {
768    /**
769     * Constructs a row iterator over this source.
770     *
771     * # Panics
772     *
773     * Panics if the row does not exist in this source.
774     */
775    #[track_caller]
776    pub fn from(source: &S, row: Row) -> RowReferenceIterator<T, S> {
777        assert!(
778            source.index_is_valid(row, 0),
779            "Expected ({},{}) to be in range",
780            row,
781            0
782        );
783        RowReferenceIterator {
784            matrix: source,
785            row,
786            range: 0..source.view_columns(),
787            _type: PhantomData,
788        }
789    }
790}
791
792impl<'a, T, S: MatrixRef<T>> Iterator for RowReferenceIterator<'a, T, S> {
793    type Item = &'a T;
794
795    fn next(&mut self) -> Option<Self::Item> {
796        match self.range.next() {
797            None => None,
798            Some(column) => unsafe {
799                // Safety: We initialised the range to 0..matrix.view_columns(), and
800                // checked we can read from this row at creation, hence if
801                // the view_columns have not changed this read is in bounds and if
802                // they are able to be changed, then the MatrixRef implementation is
803                // required to bounds check for us.
804                Some(self.matrix.get_reference_unchecked(self.row, column))
805            },
806        }
807    }
808
809    fn size_hint(&self) -> (usize, Option<usize>) {
810        self.range.size_hint()
811    }
812}
813impl<'a, T, S: MatrixRef<T>> FusedIterator for RowReferenceIterator<'a, T, S> {}
814impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for RowReferenceIterator<'a, T, S> {}
815
816/**
817 * A column major iterator over references to all values in a matrix.
818 *
819 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
820 * ```ignore
821 * [
822 *   1, 2
823 *   3, 4
824 * ]
825 * ```
826 * The elements will be iterated through as &1, &3, &2, &4
827 */
828#[derive(Debug)]
829pub struct ColumnMajorReferenceIterator<'a, T, S: MatrixRef<T> = Matrix<T>> {
830    matrix: &'a S,
831    column_counter: Column,
832    columns: Column,
833    row_counter: Row,
834    rows: Row,
835    finished: bool,
836    _type: PhantomData<&'a T>,
837}
838
839impl<'a, T> ColumnMajorReferenceIterator<'a, T> {
840    /**
841     * Constructs a column major iterator over this matrix.
842     */
843    pub fn new(matrix: &Matrix<T>) -> ColumnMajorReferenceIterator<T> {
844        ColumnMajorReferenceIterator::from(matrix)
845    }
846}
847
848impl<'a, T, S: MatrixRef<T>> ColumnMajorReferenceIterator<'a, T, S> {
849    /**
850     * Constructs a column major iterator over this source.
851     */
852    pub fn from(source: &S) -> ColumnMajorReferenceIterator<T, S> {
853        ColumnMajorReferenceIterator {
854            matrix: source,
855            column_counter: 0,
856            columns: source.view_columns(),
857            row_counter: 0,
858            rows: source.view_rows(),
859            finished: !source.index_is_valid(0, 0),
860            _type: PhantomData,
861        }
862    }
863
864    /**
865     * Constructs an iterator which also yields the row and column index of each element in
866     * this iterator.
867     */
868    pub fn with_index(self) -> WithIndex<Self> {
869        WithIndex { iterator: self }
870    }
871}
872
873impl<'a, T, S: MatrixRef<T>> From<ColumnMajorReferenceIterator<'a, T, S>>
874    for WithIndex<ColumnMajorReferenceIterator<'a, T, S>>
875{
876    fn from(iterator: ColumnMajorReferenceIterator<'a, T, S>) -> Self {
877        iterator.with_index()
878    }
879}
880
881impl<'a, T, S: MatrixRef<T>> Iterator for ColumnMajorReferenceIterator<'a, T, S> {
882    type Item = &'a T;
883
884    fn next(&mut self) -> Option<Self::Item> {
885        column_major_iter(
886            &mut self.finished,
887            self.rows,
888            self.columns,
889            &mut self.row_counter,
890            &mut self.column_counter,
891        )
892        .map(|(row, column)| unsafe {
893            // Safety: We checked on creation that 0,0 is in range, and after getting
894            // our next value we check if we hit the end of the matrix and will avoid
895            // calling this on our next loop if we finished. Hence if the view size has
896            // not changed this read is in bounds and if they are able to be changed,
897            // then the MatrixRef implementation is required to bounds check for us.
898            self.matrix.get_reference_unchecked(row, column)
899        })
900    }
901
902    fn size_hint(&self) -> (usize, Option<usize>) {
903        column_major_size_hint(
904            self.rows,
905            self.columns,
906            self.row_counter,
907            self.column_counter,
908        )
909    }
910}
911
912impl<'a, T, S: MatrixRef<T>> FusedIterator for ColumnMajorReferenceIterator<'a, T, S> {}
913impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for ColumnMajorReferenceIterator<'a, T, S> {}
914
915impl<'a, T, S: MatrixRef<T>> Iterator for WithIndex<ColumnMajorReferenceIterator<'a, T, S>> {
916    type Item = ((Row, Column), &'a T);
917
918    fn next(&mut self) -> Option<Self::Item> {
919        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
920        self.iterator.next().map(|x| ((row, column), x))
921    }
922
923    fn size_hint(&self) -> (usize, Option<usize>) {
924        self.iterator.size_hint()
925    }
926}
927impl<'a, T, S: MatrixRef<T>> FusedIterator for WithIndex<ColumnMajorReferenceIterator<'a, T, S>> {}
928/**
929 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
930 * did not return an exact size
931 */
932#[rustfmt::skip]
933impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for WithIndex<ColumnMajorReferenceIterator<'a, T, S>> {}
934
935/**
936 * A row major iterator over references to all values in a matrix.
937 *
938 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
939 * ```ignore
940 * [
941 *   1, 2
942 *   3, 4
943 * ]
944 * ```
945 * The elements will be iterated through as &1, &2, &3, &4
946 */
947#[derive(Debug)]
948pub struct RowMajorReferenceIterator<'a, T, S: MatrixRef<T> = Matrix<T>> {
949    matrix: &'a S,
950    column_counter: Column,
951    columns: Column,
952    row_counter: Row,
953    rows: Row,
954    finished: bool,
955    _type: PhantomData<&'a T>,
956}
957
958impl<'a, T> RowMajorReferenceIterator<'a, T> {
959    /**
960     * Constructs a column major iterator over this matrix.
961     */
962    pub fn new(matrix: &Matrix<T>) -> RowMajorReferenceIterator<T> {
963        RowMajorReferenceIterator::from(matrix)
964    }
965}
966
967impl<'a, T, S: MatrixRef<T>> RowMajorReferenceIterator<'a, T, S> {
968    /**
969     * Constructs a column major iterator over this source.
970     */
971    pub fn from(source: &S) -> RowMajorReferenceIterator<T, S> {
972        RowMajorReferenceIterator {
973            matrix: source,
974            column_counter: 0,
975            columns: source.view_columns(),
976            row_counter: 0,
977            rows: source.view_rows(),
978            finished: !source.index_is_valid(0, 0),
979            _type: PhantomData,
980        }
981    }
982
983    /**
984     * Constructs an iterator which also yields the row and column index of each element in
985     * this iterator.
986     */
987    pub fn with_index(self) -> WithIndex<Self> {
988        WithIndex { iterator: self }
989    }
990}
991
992impl<'a, T, S: MatrixRef<T>> From<RowMajorReferenceIterator<'a, T, S>>
993    for WithIndex<RowMajorReferenceIterator<'a, T, S>>
994{
995    fn from(iterator: RowMajorReferenceIterator<'a, T, S>) -> Self {
996        iterator.with_index()
997    }
998}
999
1000impl<'a, T, S: MatrixRef<T>> Iterator for RowMajorReferenceIterator<'a, T, S> {
1001    type Item = &'a T;
1002
1003    fn next(&mut self) -> Option<Self::Item> {
1004        row_major_iter(
1005            &mut self.finished,
1006            self.rows,
1007            self.columns,
1008            &mut self.row_counter,
1009            &mut self.column_counter,
1010        )
1011        .map(|(row, column)| unsafe {
1012            // Safety: We checked on creation that 0,0 is in range, and after getting
1013            // our next value we check if we hit the end of the matrix and will avoid
1014            // calling this on our next loop if we finished. Hence if the view size has
1015            // not changed this read is in bounds and if they are able to be changed,
1016            // then the MatrixRef implementation is required to bounds check for us.
1017            self.matrix.get_reference_unchecked(row, column)
1018        })
1019    }
1020
1021    fn size_hint(&self) -> (usize, Option<usize>) {
1022        row_major_size_hint(
1023            self.rows,
1024            self.columns,
1025            self.row_counter,
1026            self.column_counter,
1027        )
1028    }
1029}
1030impl<'a, T, S: MatrixRef<T>> FusedIterator for RowMajorReferenceIterator<'a, T, S> {}
1031impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for RowMajorReferenceIterator<'a, T, S> {}
1032
1033impl<'a, T, S: MatrixRef<T>> Iterator for WithIndex<RowMajorReferenceIterator<'a, T, S>> {
1034    type Item = ((Row, Column), &'a T);
1035
1036    fn next(&mut self) -> Option<Self::Item> {
1037        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
1038        self.iterator.next().map(|x| ((row, column), x))
1039    }
1040
1041    fn size_hint(&self) -> (usize, Option<usize>) {
1042        self.iterator.size_hint()
1043    }
1044}
1045impl<'a, T, S: MatrixRef<T>> FusedIterator for WithIndex<RowMajorReferenceIterator<'a, T, S>> {}
1046/**
1047 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
1048 * did not return an exact size
1049 */
1050impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for WithIndex<RowMajorReferenceIterator<'a, T, S>> {}
1051
1052/**
1053 * An iterator over the main diagonal in a matrix.
1054 *
1055 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1056 * ```ignore
1057 * [
1058 *   1, 2
1059 *   3, 4
1060 * ]
1061 * ```
1062 * The elements will be iterated through as 1, 4
1063 *
1064 * If the matrix is not square this will stop at whichever row/colum is shorter.
1065 */
1066#[derive(Debug)]
1067pub struct DiagonalIterator<'a, T: Clone, S: MatrixRef<T> = Matrix<T>> {
1068    matrix: &'a S,
1069    range: Range<usize>,
1070    _type: PhantomData<&'a T>,
1071}
1072
1073impl<'a, T: Clone> DiagonalIterator<'a, T> {
1074    /**
1075     * Constructs a diagonal iterator over this matrix.
1076     */
1077    pub fn new(matrix: &Matrix<T>) -> DiagonalIterator<T> {
1078        DiagonalIterator::from(matrix)
1079    }
1080}
1081
1082impl<'a, T: Clone, S: MatrixRef<T>> DiagonalIterator<'a, T, S> {
1083    /**
1084     * Constructs a diagonal iterator over this source.
1085     */
1086    pub fn from(source: &S) -> DiagonalIterator<T, S> {
1087        DiagonalIterator {
1088            matrix: source,
1089            range: 0..std::cmp::min(source.view_rows(), source.view_columns()),
1090            _type: PhantomData,
1091        }
1092    }
1093}
1094
1095impl<'a, T: Clone, S: MatrixRef<T>> Iterator for DiagonalIterator<'a, T, S> {
1096    type Item = T;
1097
1098    fn next(&mut self) -> Option<Self::Item> {
1099        match self.range.next() {
1100            None => None,
1101            Some(i) => unsafe {
1102                // Safety: We initialised the range to 0..min(rows/columns), hence if the
1103                // view size has not changed this read is in bounds and if they are able to
1104                // be changed, then the MatrixRef implementation is required to bounds
1105                // check for us.
1106                Some(self.matrix.get_reference_unchecked(i, i).clone())
1107            },
1108        }
1109    }
1110
1111    fn size_hint(&self) -> (usize, Option<usize>) {
1112        self.range.size_hint()
1113    }
1114}
1115impl<'a, T: Clone, S: MatrixRef<T>> FusedIterator for DiagonalIterator<'a, T, S> {}
1116impl<'a, T: Clone, S: MatrixRef<T>> ExactSizeIterator for DiagonalIterator<'a, T, S> {}
1117
1118/**
1119 * An iterator over references to the main diagonal in a matrix.
1120 *
1121 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1122 * ```ignore
1123 * [
1124 *   1, 2
1125 *   3, 4
1126 * ]
1127 * ```
1128 * The elements will be iterated through as &1, &4
1129 *
1130 * If the matrix is not square this will stop at whichever row/colum is shorter.
1131 */
1132#[derive(Debug)]
1133pub struct DiagonalReferenceIterator<'a, T, S: MatrixRef<T> = Matrix<T>> {
1134    matrix: &'a S,
1135    range: Range<usize>,
1136    _type: PhantomData<&'a T>,
1137}
1138
1139impl<'a, T> DiagonalReferenceIterator<'a, T> {
1140    /**
1141     * Constructs a diagonal iterator over this matrix.
1142     */
1143    pub fn new(matrix: &Matrix<T>) -> DiagonalReferenceIterator<T> {
1144        DiagonalReferenceIterator::from(matrix)
1145    }
1146}
1147
1148impl<'a, T, S: MatrixRef<T>> DiagonalReferenceIterator<'a, T, S> {
1149    /**
1150     * Constructs a diagonal iterator over this source.
1151     */
1152    pub fn from(source: &S) -> DiagonalReferenceIterator<T, S> {
1153        DiagonalReferenceIterator {
1154            matrix: source,
1155            range: 0..std::cmp::min(source.view_rows(), source.view_columns()),
1156            _type: PhantomData,
1157        }
1158    }
1159}
1160
1161impl<'a, T, S: MatrixRef<T>> Iterator for DiagonalReferenceIterator<'a, T, S> {
1162    type Item = &'a T;
1163
1164    fn next(&mut self) -> Option<Self::Item> {
1165        match self.range.next() {
1166            None => None,
1167            Some(i) => unsafe {
1168                // Safety: We initialised the range to 0..min(rows/columns), hence if the
1169                // view size has not changed this read is in bounds and if they are able to
1170                // be changed, then the MatrixRef implementation is required to bounds
1171                // check for us.
1172                Some(self.matrix.get_reference_unchecked(i, i))
1173            },
1174        }
1175    }
1176
1177    fn size_hint(&self) -> (usize, Option<usize>) {
1178        self.range.size_hint()
1179    }
1180}
1181impl<'a, T, S: MatrixRef<T>> FusedIterator for DiagonalReferenceIterator<'a, T, S> {}
1182impl<'a, T, S: MatrixRef<T>> ExactSizeIterator for DiagonalReferenceIterator<'a, T, S> {}
1183
1184/**
1185 * A column major iterator over mutable references to all values in a matrix.
1186 *
1187 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1188 * ```ignore
1189 * [
1190 *   1, 2
1191 *   3, 4
1192 * ]
1193 * ```
1194 * The elements will be iterated through as &mut 1, &mut 3, &mut 2, &mut 4
1195 */
1196#[derive(Debug)]
1197#[rustfmt::skip]
1198pub struct ColumnMajorReferenceMutIterator<'a, T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1199    matrix: &'a mut S,
1200    column_counter: Column,
1201    columns: Column,
1202    row_counter: Row,
1203    rows: Row,
1204    finished: bool,
1205    _type: PhantomData<&'a mut T>,
1206}
1207
1208impl<'a, T> ColumnMajorReferenceMutIterator<'a, T> {
1209    /**
1210     * Constructs a column major iterator over this matrix.
1211     */
1212    pub fn new(matrix: &mut Matrix<T>) -> ColumnMajorReferenceMutIterator<T> {
1213        ColumnMajorReferenceMutIterator::from(matrix)
1214    }
1215}
1216
1217impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ColumnMajorReferenceMutIterator<'a, T, S> {
1218    /**
1219     * Constructs a column major iterator over this source.
1220     */
1221    pub fn from(source: &mut S) -> ColumnMajorReferenceMutIterator<T, S> {
1222        ColumnMajorReferenceMutIterator {
1223            column_counter: 0,
1224            columns: source.view_columns(),
1225            row_counter: 0,
1226            rows: source.view_rows(),
1227            finished: !source.index_is_valid(0, 0),
1228            matrix: source,
1229            _type: PhantomData,
1230        }
1231    }
1232
1233    /**
1234     * Constructs an iterator which also yields the row and column index of each element in
1235     * this iterator.
1236     */
1237    pub fn with_index(self) -> WithIndex<Self> {
1238        WithIndex { iterator: self }
1239    }
1240}
1241
1242impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> From<ColumnMajorReferenceMutIterator<'a, T, S>>
1243    for WithIndex<ColumnMajorReferenceMutIterator<'a, T, S>>
1244{
1245    fn from(iterator: ColumnMajorReferenceMutIterator<'a, T, S>) -> Self {
1246        iterator.with_index()
1247    }
1248}
1249
1250impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1251    for ColumnMajorReferenceMutIterator<'a, T, S>
1252{
1253    type Item = &'a mut T;
1254
1255    fn next(&mut self) -> Option<Self::Item> {
1256        column_major_iter(
1257            &mut self.finished,
1258            self.rows,
1259            self.columns,
1260            &mut self.row_counter,
1261            &mut self.column_counter,
1262        )
1263        .map(|(row, column)| unsafe {
1264            // Safety: We checked on creation that 0,0 is in range, and after getting
1265            // our next value we check if we hit the end of the matrix and will avoid
1266            // calling this on our next loop if we finished. Since the view size may not
1267            // change due to NoInteriorMutability and our exclusive reference this read
1268            // is in bounds.
1269            // Safety: We are not allowed to give out overlapping mutable references,
1270            // but since we will always increment the counter on every call to next()
1271            // and stop when we reach the end no references will overlap*.
1272            // The compiler doesn't know this, so transmute the lifetime for it.
1273            // *We also require the source matrix to be NoInteriorMutability to additionally
1274            // make illegal any edge cases where some extremely exotic matrix rotates its data
1275            // inside the buffer around though a shared reference while we were iterating that
1276            // could otherwise make our cursor read the same data twice.
1277            std::mem::transmute(self.matrix.get_reference_unchecked_mut(row, column))
1278        })
1279    }
1280
1281    fn size_hint(&self) -> (usize, Option<usize>) {
1282        column_major_size_hint(
1283            self.rows,
1284            self.columns,
1285            self.row_counter,
1286            self.column_counter,
1287        )
1288    }
1289}
1290#[rustfmt::skip]
1291impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for ColumnMajorReferenceMutIterator<'a, T, S> {}
1292#[rustfmt::skip]
1293impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for ColumnMajorReferenceMutIterator<'a, T, S> {}
1294
1295impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1296    for WithIndex<ColumnMajorReferenceMutIterator<'a, T, S>>
1297{
1298    type Item = ((Row, Column), &'a mut T);
1299
1300    fn next(&mut self) -> Option<Self::Item> {
1301        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
1302        self.iterator.next().map(|x| ((row, column), x))
1303    }
1304
1305    fn size_hint(&self) -> (usize, Option<usize>) {
1306        self.iterator.size_hint()
1307    }
1308}
1309#[rustfmt::skip]
1310impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for WithIndex<ColumnMajorReferenceMutIterator<'a, T, S>> {}
1311/**
1312 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
1313 * did not return an exact size
1314 */
1315#[rustfmt::skip]
1316impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for WithIndex<ColumnMajorReferenceMutIterator<'a, T, S>> {}
1317
1318/**
1319 * A row major iterator over mutable references to all values in a matrix.
1320 *
1321 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1322 * ```ignore
1323 * [
1324 *   1, 2
1325 *   3, 4
1326 * ]
1327 * ```
1328 * The elements will be iterated through as &mut 1, &mut 2, &mut 3, &mut 4
1329 */
1330#[derive(Debug)]
1331pub struct RowMajorReferenceMutIterator<'a, T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1332    matrix: &'a mut S,
1333    column_counter: Column,
1334    columns: Column,
1335    row_counter: Row,
1336    rows: Row,
1337    finished: bool,
1338    _type: PhantomData<&'a mut T>,
1339}
1340
1341impl<'a, T> RowMajorReferenceMutIterator<'a, T> {
1342    /**
1343     * Constructs a row major iterator over this matrix.
1344     */
1345    pub fn new(matrix: &mut Matrix<T>) -> RowMajorReferenceMutIterator<T> {
1346        RowMajorReferenceMutIterator::from(matrix)
1347    }
1348}
1349
1350impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> RowMajorReferenceMutIterator<'a, T, S> {
1351    /**
1352     * Constructs a row major iterator over this source.
1353     */
1354    pub fn from(source: &mut S) -> RowMajorReferenceMutIterator<T, S> {
1355        RowMajorReferenceMutIterator {
1356            column_counter: 0,
1357            columns: source.view_columns(),
1358            row_counter: 0,
1359            rows: source.view_rows(),
1360            finished: !source.index_is_valid(0, 0),
1361            matrix: source,
1362            _type: PhantomData,
1363        }
1364    }
1365
1366    /**
1367     * Constructs an iterator which also yields the row and column index of each element in
1368     * this iterator.
1369     */
1370    pub fn with_index(self) -> WithIndex<Self> {
1371        WithIndex { iterator: self }
1372    }
1373}
1374
1375impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> From<RowMajorReferenceMutIterator<'a, T, S>>
1376    for WithIndex<RowMajorReferenceMutIterator<'a, T, S>>
1377{
1378    fn from(iterator: RowMajorReferenceMutIterator<'a, T, S>) -> Self {
1379        iterator.with_index()
1380    }
1381}
1382
1383impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1384    for RowMajorReferenceMutIterator<'a, T, S>
1385{
1386    type Item = &'a mut T;
1387
1388    fn next(&mut self) -> Option<Self::Item> {
1389        row_major_iter(
1390            &mut self.finished,
1391            self.rows,
1392            self.columns,
1393            &mut self.row_counter,
1394            &mut self.column_counter,
1395        )
1396        .map(|(row, column)| unsafe {
1397            // Safety: We checked on creation that 0,0 is in range, and after getting
1398            // our next value we check if we hit the end of the matrix and will avoid
1399            // calling this on our next loop if we finished. Since the view size may not
1400            // change due to NoInteriorMutability and our exclusive reference this read
1401            // is in bounds.
1402            // then the MatrixRef implementation is required to bounds check for us.
1403            // Safety: We are not allowed to give out overlapping mutable references,
1404            // but since we will always increment the counter on every call to next()
1405            // and stop when we reach the end no references will overlap*.
1406            // The compiler doesn't know this, so transmute the lifetime for it.
1407            // *We also require the source matrix to be NoInteriorMutability to additionally
1408            // make illegal any edge cases where some extremely exotic matrix rotates its data
1409            // inside the buffer around through a shared reference while we were iterating that
1410            // could otherwise make our cursor read the same data twice.
1411            std::mem::transmute(self.matrix.get_reference_unchecked_mut(row, column))
1412        })
1413    }
1414
1415    fn size_hint(&self) -> (usize, Option<usize>) {
1416        row_major_size_hint(
1417            self.rows,
1418            self.columns,
1419            self.row_counter,
1420            self.column_counter,
1421        )
1422    }
1423}
1424#[rustfmt::skip]
1425impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for RowMajorReferenceMutIterator<'a, T, S> {}
1426#[rustfmt::skip]
1427impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for RowMajorReferenceMutIterator<'a, T, S> {}
1428
1429impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1430    for WithIndex<RowMajorReferenceMutIterator<'a, T, S>>
1431{
1432    type Item = ((Row, Column), &'a mut T);
1433
1434    fn next(&mut self) -> Option<Self::Item> {
1435        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
1436        self.iterator.next().map(|x| ((row, column), x))
1437    }
1438
1439    fn size_hint(&self) -> (usize, Option<usize>) {
1440        self.iterator.size_hint()
1441    }
1442}
1443#[rustfmt::skip]
1444impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for WithIndex<RowMajorReferenceMutIterator<'a, T, S>> {}
1445/**
1446 * Note: On earlier versions of Easy ML (<=1.9.0), the size hint given for this impl erroneously
1447 * did not return an exact size
1448 */
1449#[rustfmt::skip]
1450impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for WithIndex<RowMajorReferenceMutIterator<'a, T, S>> {}
1451
1452/**
1453 * A column major iterator over all values in a matrix.
1454 *
1455 * This iterator does not clone the values, it returns the actual values stored in the matrix.
1456 * There is no such method to return `T` by value from a [MatrixRef]/[MatrixMut], to do
1457 * this it [replaces](std::mem::replace) the values with dummy values. Hence it can only be
1458 * created for types that implement [Default] or [ZeroOne](crate::numeric::ZeroOne)
1459 * from [Numeric](crate::numeric) which provide a means to create dummy values.
1460 *
1461 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1462 * ```ignore
1463 * [
1464 *   1, 2
1465 *   3, 4
1466 * ]
1467 * ```
1468 * The elements will be iterated through as 1, 3, 2, 4
1469 *
1470 * ```
1471 * use easy_ml::matrices::Matrix;
1472 *
1473 * #[derive(Debug, Default, Eq, PartialEq)]
1474 * struct NoClone(i32);
1475 *
1476 * let matrix = Matrix::from(vec![
1477 *     vec![ NoClone(1), NoClone(2) ],
1478 *     vec![ NoClone(3), NoClone(4) ]
1479 * ]);
1480 * let values = matrix.column_major_owned_iter(); // will use T::default() for dummy values
1481 * assert_eq!(vec![ NoClone(1), NoClone(3), NoClone(2), NoClone(4) ], values.collect::<Vec<NoClone>>());
1482 * ```
1483 */
1484#[derive(Debug)]
1485#[rustfmt::skip]
1486pub struct ColumnMajorOwnedIterator<T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1487    matrix: S,
1488    column_counter: Column,
1489    columns: Column,
1490    row_counter: Row,
1491    rows: Row,
1492    finished: bool,
1493    producer: fn() -> T,
1494}
1495
1496impl<T> ColumnMajorOwnedIterator<T> {
1497    /**
1498     * Constructs a column major iterator over this matrix.
1499     */
1500    pub fn new(matrix: Matrix<T>) -> ColumnMajorOwnedIterator<T>
1501    where
1502        T: Default,
1503    {
1504        ColumnMajorOwnedIterator::from(matrix)
1505    }
1506}
1507
1508impl<T, S: MatrixMut<T> + NoInteriorMutability> ColumnMajorOwnedIterator<T, S> {
1509    /**
1510     * Constructs a column major iterator over this source.
1511     */
1512    pub fn from(source: S) -> ColumnMajorOwnedIterator<T, S>
1513    where
1514        T: Default,
1515    {
1516        ColumnMajorOwnedIterator {
1517            column_counter: 0,
1518            columns: source.view_columns(),
1519            row_counter: 0,
1520            rows: source.view_rows(),
1521            finished: !source.index_is_valid(0, 0),
1522            matrix: source,
1523            producer: || T::default(),
1524        }
1525    }
1526
1527    /**
1528     * Constructs a column major iterator over this source.
1529     */
1530    pub fn from_numeric(source: S) -> ColumnMajorOwnedIterator<T, S>
1531    where
1532        T: crate::numeric::ZeroOne,
1533    {
1534        ColumnMajorOwnedIterator {
1535            column_counter: 0,
1536            columns: source.view_columns(),
1537            row_counter: 0,
1538            rows: source.view_rows(),
1539            finished: !source.index_is_valid(0, 0),
1540            matrix: source,
1541            producer: || T::zero(),
1542        }
1543    }
1544
1545    /**
1546     * Constructs an iterator which also yields the row and column index of each element in
1547     * this iterator.
1548     */
1549    pub fn with_index(self) -> WithIndex<Self> {
1550        WithIndex { iterator: self }
1551    }
1552}
1553
1554impl<T, S: MatrixMut<T> + NoInteriorMutability> From<ColumnMajorOwnedIterator<T, S>>
1555    for WithIndex<ColumnMajorOwnedIterator<T, S>>
1556{
1557    fn from(iterator: ColumnMajorOwnedIterator<T, S>) -> Self {
1558        iterator.with_index()
1559    }
1560}
1561
1562impl<T, S: MatrixMut<T> + NoInteriorMutability> Iterator for ColumnMajorOwnedIterator<T, S> {
1563    type Item = T;
1564
1565    fn next(&mut self) -> Option<Self::Item> {
1566        column_major_iter(
1567            &mut self.finished,
1568            self.rows,
1569            self.columns,
1570            &mut self.row_counter,
1571            &mut self.column_counter,
1572        )
1573        .map(|(row, column)| unsafe {
1574            // Safety: We checked on creation that 0,0 is in range, and after getting
1575            // our next value we check if we hit the end of the matrix and will avoid
1576            // calling this on our next loop if we finished. Since the view size may not
1577            // change due to NoInteriorMutability and our exclusive reference this read
1578            // is in bounds.
1579            // *We also require the source matrix to be NoInteriorMutability to additionally
1580            // make illegal any edge cases where some extremely exotic matrix rotates its data
1581            // inside the buffer around though a shared reference while we were iterating that
1582            // could otherwise make our cursor read the same data twice.
1583            let producer = self.producer;
1584            let dummy = producer();
1585            std::mem::replace(self.matrix.get_reference_unchecked_mut(row, column), dummy)
1586        })
1587    }
1588
1589    fn size_hint(&self) -> (usize, Option<usize>) {
1590        column_major_size_hint(
1591            self.rows,
1592            self.columns,
1593            self.row_counter,
1594            self.column_counter,
1595        )
1596    }
1597}
1598#[rustfmt::skip]
1599impl<T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for ColumnMajorOwnedIterator<T, S> {}
1600#[rustfmt::skip]
1601impl<T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for ColumnMajorOwnedIterator<T, S> {}
1602
1603impl<T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1604    for WithIndex<ColumnMajorOwnedIterator<T, S>>
1605{
1606    type Item = ((Row, Column), T);
1607
1608    fn next(&mut self) -> Option<Self::Item> {
1609        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
1610        self.iterator.next().map(|x| ((row, column), x))
1611    }
1612
1613    fn size_hint(&self) -> (usize, Option<usize>) {
1614        self.iterator.size_hint()
1615    }
1616}
1617#[rustfmt::skip]
1618impl<T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for WithIndex<ColumnMajorOwnedIterator<T, S>> {}
1619#[rustfmt::skip]
1620impl<T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for WithIndex<ColumnMajorOwnedIterator<T, S>> {}
1621
1622/**
1623 * A row major iterator over all values in a matrix.
1624 *
1625 * This iterator does not clone the values, it returns the actual values stored in the matrix.
1626 * There is no such method to return `T` by value from a [MatrixRef]/[MatrixMut], to do
1627 * this it [replaces](std::mem::replace) the values with dummy values. Hence it can only be
1628 * created for types that implement [Default] or [ZeroOne](crate::numeric::ZeroOne)
1629 * from [Numeric](crate::numeric) which provide a means to create dummy values.
1630 *
1631 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1632 * ```ignore
1633 * [
1634 *   1, 2
1635 *   3, 4
1636 * ]
1637 * ```
1638 * The elements will be iterated through as 1, 2, 3, 4
1639 *
1640 * ```
1641 * use easy_ml::matrices::Matrix;
1642 *
1643 * #[derive(Debug, Default, Eq, PartialEq)]
1644 * struct NoClone(i32);
1645 *
1646 * let matrix = Matrix::from(vec![
1647 *     vec![ NoClone(1), NoClone(2) ],
1648 *     vec![ NoClone(3), NoClone(4) ]
1649 * ]);
1650 * let values = matrix.row_major_owned_iter(); // will use T::default() for dummy values
1651 * assert_eq!(vec![ NoClone(1), NoClone(2), NoClone(3), NoClone(4) ], values.collect::<Vec<NoClone>>());
1652 * ```
1653 */
1654#[derive(Debug)]
1655pub struct RowMajorOwnedIterator<T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1656    matrix: S,
1657    column_counter: Column,
1658    columns: Column,
1659    row_counter: Row,
1660    rows: Row,
1661    finished: bool,
1662    producer: fn() -> T,
1663}
1664
1665impl<T> RowMajorOwnedIterator<T> {
1666    /**
1667     * Constructs a row major iterator over this matrix.
1668     */
1669    pub fn new(matrix: Matrix<T>) -> RowMajorOwnedIterator<T>
1670    where
1671        T: Default,
1672    {
1673        RowMajorOwnedIterator::from(matrix)
1674    }
1675}
1676
1677impl<T, S: MatrixMut<T> + NoInteriorMutability> RowMajorOwnedIterator<T, S> {
1678    /**
1679     * Constructs a row major iterator over this source.
1680     */
1681    pub fn from(source: S) -> RowMajorOwnedIterator<T, S>
1682    where
1683        T: Default,
1684    {
1685        RowMajorOwnedIterator {
1686            column_counter: 0,
1687            columns: source.view_columns(),
1688            row_counter: 0,
1689            rows: source.view_rows(),
1690            finished: !source.index_is_valid(0, 0),
1691            matrix: source,
1692            producer: || T::default(),
1693        }
1694    }
1695
1696    /**
1697     * Constructs a row major iterator over this source.
1698     */
1699    pub fn from_numeric(source: S) -> RowMajorOwnedIterator<T, S>
1700    where
1701        T: crate::numeric::ZeroOne,
1702    {
1703        RowMajorOwnedIterator {
1704            column_counter: 0,
1705            columns: source.view_columns(),
1706            row_counter: 0,
1707            rows: source.view_rows(),
1708            finished: !source.index_is_valid(0, 0),
1709            matrix: source,
1710            producer: || T::zero(),
1711        }
1712    }
1713
1714    /**
1715     * Constructs an iterator which also yields the row and column index of each element in
1716     * this iterator.
1717     */
1718    pub fn with_index(self) -> WithIndex<Self> {
1719        WithIndex { iterator: self }
1720    }
1721}
1722
1723impl<T, S: MatrixMut<T> + NoInteriorMutability> From<RowMajorOwnedIterator<T, S>>
1724    for WithIndex<RowMajorOwnedIterator<T, S>>
1725{
1726    fn from(iterator: RowMajorOwnedIterator<T, S>) -> Self {
1727        iterator.with_index()
1728    }
1729}
1730
1731impl<T, S: MatrixMut<T> + NoInteriorMutability> Iterator for RowMajorOwnedIterator<T, S> {
1732    type Item = T;
1733
1734    fn next(&mut self) -> Option<Self::Item> {
1735        row_major_iter(
1736            &mut self.finished,
1737            self.rows,
1738            self.columns,
1739            &mut self.row_counter,
1740            &mut self.column_counter,
1741        )
1742        .map(|(row, column)| unsafe {
1743            // Safety: We checked on creation that 0,0 is in range, and after getting
1744            // our next value we check if we hit the end of the matrix and will avoid
1745            // calling this on our next loop if we finished. Since the view size may not
1746            // change due to NoInteriorMutability and our exclusive reference this read
1747            // is in bounds.
1748            // *We also require the source matrix to be NoInteriorMutability to additionally
1749            // make illegal any edge cases where some extremely exotic matrix rotates its data
1750            // inside the buffer around through a shared reference while we were iterating that
1751            // could otherwise make our cursor read the same data twice.
1752            let producer = self.producer;
1753            let dummy = producer();
1754            std::mem::replace(self.matrix.get_reference_unchecked_mut(row, column), dummy)
1755        })
1756    }
1757
1758    fn size_hint(&self) -> (usize, Option<usize>) {
1759        row_major_size_hint(
1760            self.rows,
1761            self.columns,
1762            self.row_counter,
1763            self.column_counter,
1764        )
1765    }
1766}
1767#[rustfmt::skip]
1768impl<T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for RowMajorOwnedIterator<T, S> {}
1769#[rustfmt::skip]
1770impl<T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for RowMajorOwnedIterator<T, S> {}
1771
1772impl<T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1773    for WithIndex<RowMajorOwnedIterator<T, S>>
1774{
1775    type Item = ((Row, Column), T);
1776
1777    fn next(&mut self) -> Option<Self::Item> {
1778        let (row, column) = (self.iterator.row_counter, self.iterator.column_counter);
1779        self.iterator.next().map(|x| ((row, column), x))
1780    }
1781
1782    fn size_hint(&self) -> (usize, Option<usize>) {
1783        self.iterator.size_hint()
1784    }
1785}
1786#[rustfmt::skip]
1787impl<T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for WithIndex<RowMajorOwnedIterator<T, S>> {}
1788#[rustfmt::skip]
1789impl<T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for WithIndex<RowMajorOwnedIterator<T, S>> {}
1790
1791/**
1792 * An iterator over mutable references to the main diagonal in a matrix.
1793 *
1794 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1795 * ```ignore
1796 * [
1797 *   1, 2
1798 *   3, 4
1799 * ]
1800 * ```
1801 * The elements will be iterated through as &mut 1, &mut 4
1802 *
1803 * If the matrix is not square this will stop at whichever row/colum is shorter.
1804 */
1805#[derive(Debug)]
1806pub struct DiagonalReferenceMutIterator<'a, T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1807    matrix: &'a mut S,
1808    range: Range<usize>,
1809    _type: PhantomData<&'a mut T>,
1810}
1811
1812impl<'a, T> DiagonalReferenceMutIterator<'a, T> {
1813    /**
1814     * Constructs a diagonal iterator over this matrix.
1815     */
1816    pub fn new(matrix: &mut Matrix<T>) -> DiagonalReferenceMutIterator<T> {
1817        DiagonalReferenceMutIterator::from(matrix)
1818    }
1819}
1820
1821impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> DiagonalReferenceMutIterator<'a, T, S> {
1822    /**
1823     * Constructs a diagonal iterator over this source.
1824     */
1825    pub fn from(source: &mut S) -> DiagonalReferenceMutIterator<T, S> {
1826        DiagonalReferenceMutIterator {
1827            range: 0..std::cmp::min(source.view_rows(), source.view_columns()),
1828            matrix: source,
1829            _type: PhantomData,
1830        }
1831    }
1832}
1833
1834impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1835    for DiagonalReferenceMutIterator<'a, T, S>
1836{
1837    type Item = &'a mut T;
1838
1839    fn next(&mut self) -> Option<Self::Item> {
1840        match self.range.next() {
1841            None => None,
1842            Some(i) => unsafe {
1843                // Safety: We initialised the range to 0..min(rows/columns), hence this read is
1844                // in bounds because the source is NoInteriorMutability and we hold an exclusive
1845                // reference to it, so the valid bounds cannot change in size.
1846                // Safety: We are not allowed to give out overlapping mutable references,
1847                // but since we will always increment the counter on every call to next()
1848                // and stop when we reach the end no references will overlap*.
1849                // The compiler doesn't know this, so transmute the lifetime for it.
1850                // *We also require the source matrix to be NoInteriorMutability to additionally
1851                // make illegal any edge cases where some extremely exotic matrix rotates its data
1852                // inside the buffer around through a shared reference while we were iterating that
1853                // could otherwise make our cursor read the same data twice.
1854                std::mem::transmute(self.matrix.get_reference_unchecked_mut(i, i))
1855            },
1856        }
1857    }
1858
1859    fn size_hint(&self) -> (usize, Option<usize>) {
1860        self.range.size_hint()
1861    }
1862}
1863#[rustfmt::skip]
1864impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for DiagonalReferenceMutIterator<'a, T, S> {}
1865#[rustfmt::skip]
1866impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for DiagonalReferenceMutIterator<'a, T, S> {}
1867
1868/**
1869 * An iterator over mutable references to a column in a matrix.
1870 *
1871 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1872 * ```ignore
1873 * [
1874 *   1, 2
1875 *   3, 4
1876 * ]
1877 * ```
1878 * Depending on the row iterator you want to obtain,
1879 * can either iterate through &mut 1, &mut 3 or &mut 2, &mut 4.
1880 */
1881#[derive(Debug)]
1882pub struct ColumnReferenceMutIterator<'a, T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1883    matrix: &'a mut S,
1884    column: Column,
1885    range: Range<Row>,
1886    _type: PhantomData<&'a mut T>,
1887}
1888
1889impl<'a, T> ColumnReferenceMutIterator<'a, T> {
1890    /**
1891     * Constructs a column iterator over this matrix.
1892     *
1893     * # Panics
1894     *
1895     * Panics if the column does not exist in this matrix.
1896     */
1897    #[track_caller]
1898    pub fn new(matrix: &mut Matrix<T>, column: Column) -> ColumnReferenceMutIterator<T> {
1899        ColumnReferenceMutIterator::from(matrix, column)
1900    }
1901}
1902
1903impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ColumnReferenceMutIterator<'a, T, S> {
1904    /**
1905     * Constructs a column iterator over this source.
1906     *
1907     * # Panics
1908     *
1909     * Panics if the column does not exist in this source.
1910     */
1911    #[track_caller]
1912    pub fn from(source: &mut S, column: Column) -> ColumnReferenceMutIterator<T, S> {
1913        assert!(
1914            source.index_is_valid(0, column),
1915            "Expected ({},{}) to be in range",
1916            0,
1917            column
1918        );
1919        ColumnReferenceMutIterator {
1920            range: 0..source.view_rows(),
1921            matrix: source,
1922            column,
1923            _type: PhantomData,
1924        }
1925    }
1926}
1927
1928impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator
1929    for ColumnReferenceMutIterator<'a, T, S>
1930{
1931    type Item = &'a mut T;
1932
1933    fn next(&mut self) -> Option<Self::Item> {
1934        match self.range.next() {
1935            None => None,
1936            Some(row) => unsafe {
1937                // Safety: We initialised the range to 0..matrix.view_rows(), and
1938                // checked we can read from this column at creation, hence this read is
1939                // in bounds because the source is NoInteriorMutability and we hold an exclusive
1940                // reference to it, so the valid bounds cannot change in size.
1941                // Safety: We are not allowed to give out overlapping mutable references,
1942                // but since we will always increment the counter on every call to next()
1943                // and stop when we reach the end no references will overlap*.
1944                // The compiler doesn't know this, so transmute the lifetime for it.
1945                // *We also require the source matrix to be NoInteriorMutability to additionally
1946                // make illegal any edge cases where some extremely exotic matrix rotates its data
1947                // inside the buffer around through a shared reference while we were iterating that
1948                // could otherwise make our cursor read the same data twice.
1949                std::mem::transmute(self.matrix.get_reference_unchecked_mut(row, self.column))
1950            },
1951        }
1952    }
1953
1954    fn size_hint(&self) -> (usize, Option<usize>) {
1955        self.range.size_hint()
1956    }
1957}
1958#[rustfmt::skip]
1959impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for ColumnReferenceMutIterator<'a, T, S> {}
1960#[rustfmt::skip]
1961impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for ColumnReferenceMutIterator<'a, T, S> {}
1962
1963/**
1964 * An iterator over mutable references to a row in a matrix.
1965 *
1966 * For a 2x2 matrix such as `[ 1, 2; 3, 4]`: ie
1967 * ```ignore
1968 * [
1969 *   1, 2
1970 *   3, 4
1971 * ]
1972 * ```
1973 * Depending on the row iterator you want to obtain,
1974 * can either iterate through &mut 1, &mut 2 or &mut 3, &mut 4.
1975 */
1976#[derive(Debug)]
1977pub struct RowReferenceMutIterator<'a, T, S: MatrixMut<T> + NoInteriorMutability = Matrix<T>> {
1978    matrix: &'a mut S,
1979    row: Row,
1980    range: Range<Column>,
1981    _type: PhantomData<&'a mut T>,
1982}
1983
1984impl<'a, T> RowReferenceMutIterator<'a, T> {
1985    /**
1986     * Constructs a row iterator over this matrix.
1987     *
1988     * # Panics
1989     *
1990     * Panics if the row does not exist in this matrix.
1991     */
1992    #[track_caller]
1993    pub fn new(matrix: &mut Matrix<T>, row: Row) -> RowReferenceMutIterator<T> {
1994        RowReferenceMutIterator::from(matrix, row)
1995    }
1996}
1997
1998impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> RowReferenceMutIterator<'a, T, S> {
1999    /**
2000     * Constructs a row iterator over this source.
2001     *
2002     * # Panics
2003     *
2004     * Panics if the row does not exist in this source.
2005     */
2006    #[track_caller]
2007    pub fn from(source: &mut S, row: Row) -> RowReferenceMutIterator<T, S> {
2008        assert!(
2009            source.index_is_valid(row, 0),
2010            "Expected ({},{}) to be in range",
2011            row,
2012            0
2013        );
2014        RowReferenceMutIterator {
2015            range: 0..source.view_columns(),
2016            matrix: source,
2017            row,
2018            _type: PhantomData,
2019        }
2020    }
2021}
2022
2023impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> Iterator for RowReferenceMutIterator<'a, T, S> {
2024    type Item = &'a mut T;
2025
2026    fn next(&mut self) -> Option<Self::Item> {
2027        match self.range.next() {
2028            None => None,
2029            Some(column) => unsafe {
2030                // Safety: We initialised the range to 0..matrix.view_columns(), and
2031                // checked we can read from this row at creation, hence this read is
2032                // in bounds because the source is NoInteriorMutability and we hold an exclusive
2033                // reference to it, so the valid bounds cannot change in size.
2034                // Safety: We are not allowed to give out overlapping mutable references,
2035                // but since we will always increment the counter on every call to next()
2036                // and stop when we reach the end no references will overlap*.
2037                // The compiler doesn't know this, so transmute the lifetime for it.
2038                // *We also require the source matrix to be NoInteriorMutability to additionally
2039                // make illegal any edge cases where some extremely exotic matrix rotates its data
2040                // inside the buffer around through a shared reference while we were iterating that
2041                // could otherwise make our cursor read the same data twice.
2042                std::mem::transmute(self.matrix.get_reference_unchecked_mut(self.row, column))
2043            },
2044        }
2045    }
2046
2047    fn size_hint(&self) -> (usize, Option<usize>) {
2048        self.range.size_hint()
2049    }
2050}
2051#[rustfmt::skip]
2052impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> FusedIterator for RowReferenceMutIterator<'a, T, S> {}
2053#[rustfmt::skip]
2054impl<'a, T, S: MatrixMut<T> + NoInteriorMutability> ExactSizeIterator for RowReferenceMutIterator<'a, T, S> {}