1use crate::{Shape, Stride, Unbind};
2use core::marker::PhantomData;
3use core::ptr::NonNull;
4use faer_traits::{ComplexField, Conjugate};
5use reborrow::*;
6
7pub(crate) struct MatView<T: ?Sized, Rows, Cols, RStride, CStride> {
8 ptr: NonNull<T>,
9 nrows: Rows,
10 ncols: Cols,
11 row_stride: RStride,
12 col_stride: CStride,
13}
14
15pub trait MatIndex<RowRange, ColRange> {
17 type Target;
19
20 fn get(this: Self, row: RowRange, col: ColRange) -> Self::Target;
22
23 unsafe fn get_unchecked(this: Self, row: RowRange, col: ColRange) -> Self::Target;
25}
26
27impl<T: ?Sized, Rows: Copy, Cols: Copy, RStride: Copy, CStride: Copy> Copy for MatView<T, Rows, Cols, RStride, CStride> {}
28impl<T: ?Sized, Rows: Copy, Cols: Copy, RStride: Copy, CStride: Copy> Clone for MatView<T, Rows, Cols, RStride, CStride> {
29 #[inline]
30 fn clone(&self) -> Self {
31 *self
32 }
33}
34
35#[inline]
36#[track_caller]
37fn from_slice_assert(nrows: usize, ncols: usize, len: usize) {
38 let size = usize::checked_mul(nrows, ncols);
39 assert!(size == Some(len));
40}
41
42mod mat_index;
43
44pub(crate) mod matmut;
45pub(crate) mod matown;
46pub(crate) mod matref;
47
48pub use matmut::Mut;
49pub use matown::Own;
50pub use matref::Ref;
51
52pub type Mat<T, Rows = usize, Cols = usize> = generic::Mat<Own<T, Rows, Cols>>;
80
81pub type MatRef<'a, T, Rows = usize, Cols = usize, RStride = isize, CStride = isize> = generic::Mat<Ref<'a, T, Rows, Cols, RStride, CStride>>;
90
91pub type MatMut<'a, T, Rows = usize, Cols = usize, RStride = isize, CStride = isize> = generic::Mat<Mut<'a, T, Rows, Cols, RStride, CStride>>;
136
137pub mod generic {
139 use crate::{Idx, Shape, Stride};
140 use core::fmt::Debug;
141 use core::ops::{Index, IndexMut};
142 use reborrow::*;
143
144 #[derive(Copy, Clone)]
146 #[repr(transparent)]
147 pub struct Mat<Inner>(pub Inner);
148
149 impl<Inner: Debug> Debug for Mat<Inner> {
150 #[inline(always)]
151 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
152 self.0.fmt(f)
153 }
154 }
155
156 impl<Inner> Mat<Inner> {
157 #[inline(always)]
159 pub fn from_inner_ref(inner: &Inner) -> &Self {
160 unsafe { &*(inner as *const Inner as *const Self) }
161 }
162
163 #[inline(always)]
165 pub fn from_inner_mut(inner: &mut Inner) -> &mut Self {
166 unsafe { &mut *(inner as *mut Inner as *mut Self) }
167 }
168 }
169
170 impl<Inner> core::ops::Deref for Mat<Inner> {
171 type Target = Inner;
172
173 #[inline(always)]
174 fn deref(&self) -> &Self::Target {
175 &self.0
176 }
177 }
178
179 impl<Inner> core::ops::DerefMut for Mat<Inner> {
180 #[inline(always)]
181 fn deref_mut(&mut self) -> &mut Self::Target {
182 &mut self.0
183 }
184 }
185
186 impl<'short, Inner: Reborrow<'short>> Reborrow<'short> for Mat<Inner> {
187 type Target = Mat<Inner::Target>;
188
189 #[inline(always)]
190 fn rb(&'short self) -> Self::Target {
191 Mat(self.0.rb())
192 }
193 }
194
195 impl<'short, Inner: ReborrowMut<'short>> ReborrowMut<'short> for Mat<Inner> {
196 type Target = Mat<Inner::Target>;
197
198 #[inline(always)]
199 fn rb_mut(&'short mut self) -> Self::Target {
200 Mat(self.0.rb_mut())
201 }
202 }
203
204 impl<Inner: IntoConst> IntoConst for Mat<Inner> {
205 type Target = Mat<Inner::Target>;
206
207 #[inline(always)]
208 fn into_const(self) -> Self::Target {
209 Mat(self.0.into_const())
210 }
211 }
212
213 impl<
214 T,
215 Rows: Shape,
216 Cols: Shape,
217 RStride: Stride,
218 CStride: Stride,
219 Inner: for<'short> Reborrow<'short, Target = super::Ref<'short, T, Rows, Cols, RStride, CStride>>,
220 > Index<(Idx<Rows>, Idx<Cols>)> for Mat<Inner>
221 {
222 type Output = T;
223
224 #[inline]
225 #[track_caller]
226 fn index(&self, (row, col): (Idx<Rows>, Idx<Cols>)) -> &Self::Output {
227 self.rb().at(row, col)
228 }
229 }
230
231 impl<
232 T,
233 Rows: Shape,
234 Cols: Shape,
235 RStride: Stride,
236 CStride: Stride,
237 Inner: for<'short> Reborrow<'short, Target = super::Ref<'short, T, Rows, Cols, RStride, CStride>>
238 + for<'short> ReborrowMut<'short, Target = super::Mut<'short, T, Rows, Cols, RStride, CStride>>,
239 > IndexMut<(Idx<Rows>, Idx<Cols>)> for Mat<Inner>
240 {
241 #[inline]
242 #[track_caller]
243 fn index_mut(&mut self, (row, col): (Idx<Rows>, Idx<Cols>)) -> &mut Self::Output {
244 self.rb_mut().at_mut(row, col)
245 }
246 }
247}
248
249pub trait AsMatRef {
251 type T;
253 type Rows: Shape;
255 type Cols: Shape;
257 type Owned: AsMat<Self::T, T = Self::T, Rows = Self::Rows, Cols = Self::Cols, Owned = Self::Owned>;
259
260 fn as_mat_ref(&self) -> MatRef<Self::T, Self::Rows, Self::Cols>;
262}
263
264pub trait AsMatMut: AsMatRef {
266 fn as_mat_mut(&mut self) -> MatMut<Self::T, Self::Rows, Self::Cols>;
268}
269
270pub trait AsMat<T>: AsMatMut {
272 fn zeros(rows: Self::Rows, cols: Self::Cols) -> Self
274 where
275 T: ComplexField;
276
277 fn truncate(&mut self, rows: Self::Rows, cols: Self::Cols);
279}
280
281impl<M: AsMatRef> AsMatRef for &M {
282 type Cols = M::Cols;
283 type Owned = M::Owned;
284 type Rows = M::Rows;
285 type T = M::T;
286
287 #[inline]
288 fn as_mat_ref(&self) -> MatRef<Self::T, Self::Rows, Self::Cols> {
289 (**self).as_mat_ref()
290 }
291}
292impl<M: AsMatRef> AsMatRef for &mut M {
293 type Cols = M::Cols;
294 type Owned = M::Owned;
295 type Rows = M::Rows;
296 type T = M::T;
297
298 #[inline]
299 fn as_mat_ref(&self) -> MatRef<Self::T, Self::Rows, Self::Cols> {
300 (**self).as_mat_ref()
301 }
302}
303impl<M: AsMatMut> AsMatMut for &mut M {
304 #[inline]
305 fn as_mat_mut(&mut self) -> MatMut<Self::T, Self::Rows, Self::Cols> {
306 (**self).as_mat_mut()
307 }
308}
309
310impl<T, Rows: Shape, Cols: Shape, RStride: Stride, CStride: Stride> AsMatRef for MatRef<'_, T, Rows, Cols, RStride, CStride> {
311 type Cols = Cols;
312 type Owned = Mat<T, Rows, Cols>;
313 type Rows = Rows;
314 type T = T;
315
316 #[inline]
317 fn as_mat_ref(&self) -> MatRef<T, Rows, Cols> {
318 self.as_dyn_stride()
319 }
320}
321
322impl<T, Rows: Shape, Cols: Shape, RStride: Stride, CStride: Stride> AsMatRef for MatMut<'_, T, Rows, Cols, RStride, CStride> {
323 type Cols = Cols;
324 type Owned = Mat<T, Rows, Cols>;
325 type Rows = Rows;
326 type T = T;
327
328 #[inline]
329 fn as_mat_ref(&self) -> MatRef<T, Rows, Cols> {
330 self.rb().as_dyn_stride()
331 }
332}
333
334impl<T, Rows: Shape, Cols: Shape, RStride: Stride, CStride: Stride> AsMatMut for MatMut<'_, T, Rows, Cols, RStride, CStride> {
335 #[inline]
336 fn as_mat_mut(&mut self) -> MatMut<T, Rows, Cols> {
337 self.rb_mut().as_dyn_stride_mut()
338 }
339}
340
341impl<T, Rows: Shape, Cols: Shape> AsMatRef for Mat<T, Rows, Cols> {
342 type Cols = Cols;
343 type Owned = Mat<T, Rows, Cols>;
344 type Rows = Rows;
345 type T = T;
346
347 #[inline]
348 fn as_mat_ref(&self) -> MatRef<T, Rows, Cols> {
349 self.as_dyn_stride()
350 }
351}
352
353impl<T, Rows: Shape, Cols: Shape> AsMat<T> for Mat<T, Rows, Cols> {
354 #[inline]
355 fn zeros(rows: Rows, cols: Cols) -> Self
356 where
357 T: ComplexField,
358 {
359 Mat::zeros(rows, cols)
360 }
361
362 #[track_caller]
363 #[inline]
364 fn truncate(&mut self, rows: Self::Rows, cols: Self::Cols) {
365 self.truncate(rows, cols)
366 }
367}
368
369impl<T, Rows: Shape, Cols: Shape> AsMatMut for Mat<T, Rows, Cols> {
370 #[inline]
371 fn as_mat_mut(&mut self) -> MatMut<T, Rows, Cols> {
372 self.as_dyn_stride_mut()
373 }
374}
375
376#[cfg(test)]
377mod tests {
378 use super::*;
379 use crate::prelude::*;
380
381 #[test]
382 fn test_mat() {
383 let _x = crate::mat![[0.0, 1.0]];
384 let mat = Mat::from_fn(3, 4, |i, j| i as f64 + j as f64);
385
386 let mat = mat.as_ref().cloned();
387 let mat = mat.as_ref();
388
389 for i in 0..3 {
390 for j in 0..4 {
391 zip!(&mat).map(|x| x).as_ref().at(i, j);
392 }
393 }
394 }
395
396 #[test]
397 fn test_mat_complex() {
398 let _x = mat![[c64::new(0.0, 0.0), c64::new(1.0, 0.0)]];
399 let mat = Mat::from_fn(3, 4, |i, j| c64::new(i as f64 + j as f64, 0.0));
400 {
401 let _conj = mat.as_ref().conjugate();
402 }
403
404 let mat = mat.as_ref().cloned();
405 let mat = mat.as_ref();
406
407 for i in 0..3 {
408 for j in 0..4 {
409 zip!(&mat).map(|x| x).as_ref().at(i, j);
410 }
411 }
412 }
413}