mech_core/
matrix.rs

1use crate::*;
2use crate::types::Ref;
3use na::{Vector3, DVector, Vector2, Vector4, RowDVector, Matrix1, Matrix3, Matrix4, RowVector3, RowVector4, RowVector2, DMatrix, Rotation3, Matrix2x3, Matrix3x2, Matrix6, Matrix2};
4use tabled::{
5    builder::Builder,
6    settings::{object::Rows,Panel, Span, Alignment, Modify, Style},
7    Tabled,
8  };
9use std::fmt::{Debug, Display};
10use std::hash::{Hash, Hasher};
11use std::slice::Iter;
12use std::iter::Peekable;
13use serde::ser::{Serialize, Serializer, SerializeStruct};
14use std::any::Any;
15
16// Matrix ---------------------------------------------------------------------
17
18pub trait ToMatrix: Clone {
19  fn to_matrix(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self>;
20  fn to_matrixd(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self>;
21}
22  
23macro_rules! impl_to_matrix {
24  ($t:ty) => {
25    impl ToMatrix for $t {
26      fn to_matrix(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self> {
27        match (rows,cols) {
28          #[cfg(feature = "Matrix1")]
29          (1,1) => Matrix::Matrix1(new_ref(Matrix1::from_element(elements[0].clone()))),
30          #[cfg(feature = "Matrix2")]
31          (2,2) => Matrix::Matrix2(new_ref(Matrix2::from_vec(elements))),
32          #[cfg(feature = "Matrix3")]
33          (3,3) => Matrix::Matrix3(new_ref(Matrix3::from_vec(elements))),
34          #[cfg(feature = "Matrix4")]
35          (4,4) => Matrix::Matrix4(new_ref(Matrix4::from_vec(elements))),
36          #[cfg(feature = "Matrix2x3")]
37          (2,3) => Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(elements))),
38          #[cfg(feature = "Matrix3x2")]
39          (3,2) => Matrix::Matrix3x2(new_ref(Matrix3x2::from_vec(elements))),
40          #[cfg(feature = "RowVector2")]
41          (1,2) => Matrix::RowVector2(new_ref(RowVector2::from_vec(elements))),
42          #[cfg(feature = "RowVector3")]
43          (1,3) => Matrix::RowVector3(new_ref(RowVector3::from_vec(elements))),
44          #[cfg(feature = "RowVector4")]
45          (1,4) => Matrix::RowVector4(new_ref(RowVector4::from_vec(elements))),
46          #[cfg(feature = "Vector2")]
47          (2,1) => Matrix::Vector2(new_ref(Vector2::from_vec(elements))),
48          #[cfg(feature = "Vector2")]
49          (3,1) => Matrix::Vector3(new_ref(Vector3::from_vec(elements))),
50          #[cfg(feature = "Vector2")]
51          (4,1) => Matrix::Vector4(new_ref(Vector4::from_vec(elements))),
52          #[cfg(feature = "RowVectorD")]
53          (1,n) => Matrix::RowDVector(new_ref(RowDVector::from_vec(elements))),
54          #[cfg(feature = "VectorD")]
55          (m,1) => Matrix::DVector(new_ref(DVector::from_vec(elements))),
56          #[cfg(feature = "MatrixD")]
57          (m,n) => Matrix::DMatrix(new_ref(DMatrix::from_vec(m,n,elements))),
58        }
59      }
60      fn to_matrixd(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self> {
61        match (rows,cols) {
62          #[cfg(feature = "RowVectorD")]
63          (1,n) => Matrix::RowDVector(new_ref(RowDVector::from_vec(elements))),
64          #[cfg(feature = "VectorD")]
65          (m,1) => Matrix::DVector(new_ref(DVector::from_vec(elements))),
66          #[cfg(feature = "MatrixD")]
67          (m,n) => Matrix::DMatrix(new_ref(DMatrix::from_vec(m,n,elements))),
68        }
69      }
70    }
71  };    
72}
73
74impl ToMatrix for usize {
75  fn to_matrix(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self> {
76    match (rows,cols) {
77      #[cfg(feature = "RowVectorD")]
78      (1,n) => Matrix::RowDVector(new_ref(RowDVector::from_vec(elements))),
79      #[cfg(feature = "VectorD")]
80      (m,1) => Matrix::DVector(new_ref(DVector::from_vec(elements))),
81      #[cfg(feature = "MatrixD")]
82      (m,n) => Matrix::DMatrix(new_ref(DMatrix::from_vec(m,n,elements))),
83    }
84  }
85  fn to_matrixd(elements: Vec<Self>, rows: usize, cols: usize) -> Matrix<Self> {
86    match (rows,cols) {
87      #[cfg(feature = "RowVectorD")]
88      (1,n) => Matrix::RowDVector(new_ref(RowDVector::from_vec(elements))),
89      #[cfg(feature = "VectorD")]
90      (m,1) => Matrix::DVector(new_ref(DVector::from_vec(elements))),
91      #[cfg(feature = "MatrixD")]
92      (m,n) => Matrix::DMatrix(new_ref(DMatrix::from_vec(m,n,elements))),
93    }
94  }
95}
96
97impl_to_matrix!(Value);
98#[cfg(feature = "Bool")]
99impl_to_matrix!(bool);
100#[cfg(feature = "U8")]
101impl_to_matrix!(u8);
102#[cfg(feature = "U16")]
103impl_to_matrix!(u16);
104#[cfg(feature = "U32")]
105impl_to_matrix!(u32);
106#[cfg(feature = "U64")]
107impl_to_matrix!(u64);
108#[cfg(feature = "U128")]
109impl_to_matrix!(u128);
110#[cfg(feature = "I8")]
111impl_to_matrix!(i8);
112#[cfg(feature = "I16")]
113impl_to_matrix!(i16);
114#[cfg(feature = "I32")]
115impl_to_matrix!(i32);
116#[cfg(feature = "I64")]
117impl_to_matrix!(i64);
118#[cfg(feature = "I128")]
119impl_to_matrix!(i128);
120#[cfg(feature = "F32")]
121impl_to_matrix!(F32);
122#[cfg(feature = "F64")]
123impl_to_matrix!(F64);
124#[cfg(feature = "String")]
125impl_to_matrix!(String);
126#[cfg(feature = "ComplexNumber")]
127impl_to_matrix!(ComplexNumber);
128#[cfg(feature = "RationalNumber")]
129impl_to_matrix!(RationalNumber);
130  
131pub trait ToIndex: Clone {
132  fn to_index(elements: Vec<Self>) -> Matrix<Self>;
133}
134
135#[derive(Clone, Debug, PartialEq, Eq)]
136pub enum Matrix<T> {
137  #[cfg(feature = "RowVector4")]
138  RowVector4(Ref<RowVector4<T>>),
139  #[cfg(feature = "RowVector3")]
140  RowVector3(Ref<RowVector3<T>>),
141  #[cfg(feature = "RowVector2")]
142  RowVector2(Ref<RowVector2<T>>),
143  #[cfg(feature = "RowVectorD")]
144  RowDVector(Ref<RowDVector<T>>),
145  #[cfg(feature = "Vector4")]
146  Vector4(Ref<Vector4<T>>),  
147  #[cfg(feature = "Vector3")]
148  Vector3(Ref<Vector3<T>>),
149  #[cfg(feature = "Vector2")]
150  Vector2(Ref<Vector2<T>>),
151  #[cfg(feature = "VectorD")]
152  DVector(Ref<DVector<T>>),
153  #[cfg(feature = "Matrix4")]
154  Matrix4(Ref<Matrix4<T>>),
155  #[cfg(feature = "Matrix3")]
156  Matrix3(Ref<Matrix3<T>>),
157  #[cfg(feature = "Matrix2")]
158  Matrix2(Ref<Matrix2<T>>),
159  #[cfg(feature = "Matrix1")]
160  Matrix1(Ref<Matrix1<T>>),
161  #[cfg(feature = "Matrix3x2")]
162  Matrix3x2(Ref<Matrix3x2<T>>),
163  #[cfg(feature = "Matrix2x3")]
164  Matrix2x3(Ref<Matrix2x3<T>>),
165  #[cfg(feature = "MatrixD")]
166  DMatrix(Ref<DMatrix<T>>),
167}
168
169pub trait CopyMat<T> {
170  fn copy_into(&self, dst: &Ref<DMatrix<T>>, offset: usize) -> usize;
171  fn copy_into_v(&self, dst: &Ref<DVector<T>>, offset: usize) -> usize;
172  fn copy_into_r(&self, dst: &Ref<RowDVector<T>>, offset: usize) -> usize;
173  fn copy_into_row_major(&self, dst: &Ref<DMatrix<T>>, offset: usize) -> usize;
174}
175
176macro_rules! copy_mat {
177  ($matsize:ident) => {
178    impl<T> CopyMat<T> for Ref<$matsize<T>> 
179    where T: Clone 
180    {
181      fn copy_into(&self, dst: &Ref<DMatrix<T>>, offset: usize) -> usize {
182        let src_ptr = unsafe { (*(self.as_ptr())).clone() };
183        let mut dst_ptr = unsafe { &mut *(dst.as_ptr()) };
184        for i in 0..src_ptr.len() {
185            dst_ptr[i + offset] = src_ptr[i].clone();
186        }
187        src_ptr.len()
188      }
189      fn copy_into_v(&self, dst: &Ref<DVector<T>>, offset: usize) -> usize {
190        let src_ptr = unsafe { (*(self.as_ptr())).clone() };
191        let mut dst_ptr = unsafe { &mut *(dst.as_ptr()) };
192        for i in 0..src_ptr.len() {
193            dst_ptr[i + offset] = src_ptr[i].clone();
194        }
195        src_ptr.len()
196      }
197      fn copy_into_r(&self, dst: &Ref<RowDVector<T>>, offset: usize) -> usize {
198        let src_ptr = unsafe { (*(self.as_ptr())).clone() };
199        let mut dst_ptr = unsafe { &mut *(dst.as_ptr()) };
200        for i in 0..src_ptr.len() {
201            dst_ptr[i + offset] = src_ptr[i].clone();
202        }
203        src_ptr.len()
204      }
205      fn copy_into_row_major(&self, dst: &Ref<DMatrix<T>>, offset: usize) -> usize {
206        let src_ptr = unsafe { (*(self.as_ptr())).clone() };
207        let mut dst_ptr = unsafe { &mut *(dst.as_ptr()) };
208        let src_rows = src_ptr.nrows();
209        let dest_rows = dst_ptr.nrows();
210
211        let stride = dest_rows - src_rows;
212        let mut offset = offset;
213        for ix in 0..src_ptr.len() {
214            dst_ptr[offset] = src_ptr[ix].clone();
215            offset += ((ix + 1) % src_rows == 0) as usize * stride + 1;
216        }
217        src_rows
218      }}};}
219      
220#[cfg(feature = "MatrixD")]
221copy_mat!(DMatrix);
222#[cfg(feature = "Matrix1")]
223copy_mat!(Matrix1);
224#[cfg(feature = "Matrix2")]
225copy_mat!(Matrix2);
226#[cfg(feature = "Matrix3")]
227copy_mat!(Matrix3);
228#[cfg(feature = "Matrix4")]
229copy_mat!(Matrix4);
230#[cfg(feature = "Matrix2x3")]
231copy_mat!(Matrix2x3);
232#[cfg(feature = "Matrix3x2")]
233copy_mat!(Matrix3x2);
234#[cfg(feature = "Vector2")]
235copy_mat!(Vector2);
236#[cfg(feature = "Vector3")]
237copy_mat!(Vector3);
238#[cfg(feature = "Vector4")]
239copy_mat!(Vector4);
240#[cfg(feature = "VectorD")]
241copy_mat!(DVector);
242#[cfg(feature = "RowVector2")]
243copy_mat!(RowVector2);
244#[cfg(feature = "RowVector3")]
245copy_mat!(RowVector3);
246#[cfg(feature = "RowVector4")]
247copy_mat!(RowVector4);
248#[cfg(feature = "RowVectorD")]
249copy_mat!(RowDVector);
250
251impl<T> Hash for Matrix<T> 
252where T: Hash + na::Scalar
253{
254  fn hash<H: Hasher>(&self, state: &mut H) {
255    match self {
256      #[cfg(feature = "RowVector4")]
257      Matrix::RowVector4(x) => x.borrow().hash(state),
258      #[cfg(feature = "RowVector3")]
259      Matrix::RowVector3(x) => x.borrow().hash(state),
260      #[cfg(feature = "RowVector2")]
261      Matrix::RowVector2(x) => x.borrow().hash(state),
262      #[cfg(feature = "RowVectorD")]
263      Matrix::RowDVector(x) => x.borrow().hash(state),
264      #[cfg(feature = "Vector4")]
265      Matrix::Vector4(x) => x.borrow().hash(state),
266      #[cfg(feature = "Vector3")]
267      Matrix::Vector3(x) => x.borrow().hash(state),
268      #[cfg(feature = "Vector2")]
269      Matrix::Vector2(x) => x.borrow().hash(state),
270      #[cfg(feature = "VectorD")]
271      Matrix::DVector(x) => x.borrow().hash(state),
272      #[cfg(feature = "Matrix4")]
273      Matrix::Matrix4(x) => x.borrow().hash(state),
274      #[cfg(feature = "Matrix3")]
275      Matrix::Matrix3(x) => x.borrow().hash(state),
276      #[cfg(feature = "Matrix2")]
277      Matrix::Matrix2(x) => x.borrow().hash(state),
278      #[cfg(feature = "Matrix1")]
279      Matrix::Matrix1(x) => x.borrow().hash(state),
280      #[cfg(feature = "Matrix3x2")]
281      Matrix::Matrix3x2(x) => x.borrow().hash(state),
282      #[cfg(feature = "Matrix2x3")]
283      Matrix::Matrix2x3(x) => x.borrow().hash(state),
284      #[cfg(feature = "MatrixD")]
285      Matrix::DMatrix(x) => x.borrow().hash(state),
286    }
287  }
288}
289
290
291pub trait PrettyPrint {
292  fn pretty_print(&self) -> String;
293}
294
295impl PrettyPrint for String {
296  fn pretty_print(&self) -> String {
297      format!("\"{}\"", self)
298  }
299}
300
301impl PrettyPrint for Value {
302  fn  pretty_print(&self) -> String {
303    self.pretty_print()
304  }
305}
306
307macro_rules! impl_pretty_print {
308  ($t:ty) => {
309    impl PrettyPrint for $t {
310      fn pretty_print(&self) -> String {
311        format!("{}", self)
312      }
313    }
314  };
315}
316
317impl_pretty_print!(bool);
318impl_pretty_print!(i8);
319impl_pretty_print!(i16);
320impl_pretty_print!(i32);
321impl_pretty_print!(i64);
322impl_pretty_print!(i128);
323impl_pretty_print!(u8);
324impl_pretty_print!(u16);
325impl_pretty_print!(u32);
326impl_pretty_print!(u64);
327impl_pretty_print!(u128);
328impl_pretty_print!(F32);
329impl_pretty_print!(F64);
330impl_pretty_print!(usize);
331
332impl<T> PrettyPrint for Matrix<T>
333where T: Debug + Display + Clone + PartialEq + 'static + PrettyPrint
334{
335  fn pretty_print(&self) -> String {
336    let mut builder = Builder::default();
337    match self {
338      #[cfg(feature = "RowVector4")]
339      Matrix::RowVector4(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
340      #[cfg(feature = "RowVector3")]
341      Matrix::RowVector3(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
342      #[cfg(feature = "RowVector2")]
343      Matrix::RowVector2(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
344      #[cfg(feature = "RowVectorD")]
345      Matrix::RowDVector(vec) => {
346        let vec_brrw = vec.borrow();
347        let vec_str = if vec_brrw.ncols() > 20 {
348          let mut vec_str = vec_brrw.row(0).iter().take(10).chain(vec_brrw.row(0).iter().rev().take(9).rev()).map(|x| x.pretty_print()).collect::<Vec<_>>();
349          vec_str.insert(10,"...".to_string());
350          vec_str
351        } else {
352          vec_brrw.row(0).iter().map(|x| format!("{:?}", x)).collect::<Vec<_>>()
353        };
354        builder.push_record(vec_str);
355      }
356      #[cfg(feature = "Vector4")]
357      Matrix::Vector4(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
358      #[cfg(feature = "Vector3")]
359      Matrix::Vector3(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
360      #[cfg(feature = "Vector2")]
361      Matrix::Vector2(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
362      #[cfg(feature = "VectorD")]
363      Matrix::DVector(vec) => {
364        let vec_brrw = vec.borrow();
365        let vec_str = if vec_brrw.nrows() > 20 {
366          let mut vec_str = vec_brrw.column(0).iter().take(10).chain(vec_brrw.column(0).iter().rev().take(9).rev()).map(|x| x.pretty_print()).collect::<Vec<_>>();
367          vec_str.insert(10,"...".to_string());
368          vec_str
369        } else {
370          vec_brrw.column(0).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()
371        };
372        for r in vec_str {
373          builder.push_record(vec![r]);
374        }
375      }
376      #[cfg(feature = "Matrix4")]
377      Matrix::Matrix4(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
378      #[cfg(feature = "Matrix3")]
379      Matrix::Matrix3(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
380      #[cfg(feature = "Matrix2")]
381      Matrix::Matrix2(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
382      #[cfg(feature = "Matrix1")]
383      Matrix::Matrix1(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
384      #[cfg(feature = "Matrix3x2")]
385      Matrix::Matrix3x2(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
386      #[cfg(feature = "Matrix2x3")]
387      Matrix::Matrix2x3(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
388      #[cfg(feature = "MatrixD")]
389      Matrix::DMatrix(vec) => {let vec_brrw = vec.borrow();(0..vec_brrw.nrows()).for_each(|i| builder.push_record(vec_brrw.row(i).iter().map(|x| x.pretty_print()).collect::<Vec<_>>()));}
390      _ => todo!(),
391    };
392    let matrix_style = Style::empty()
393      .top(' ')
394      .left('┃')
395      .right('┃')
396      .bottom(' ')
397      .vertical(' ')
398      .intersection_bottom(' ')
399      .corner_top_left('┏')
400      .corner_top_right('┓')
401      .corner_bottom_left('┗')
402      .corner_bottom_right('┛');
403    let mut table = builder.build();
404    table.with(matrix_style);
405    format!("{table}")
406  }
407}
408
409fn quoted<T: Display + Any>(val: &T) -> String {
410  if let Some(s) = (val as &dyn Any).downcast_ref::<String>() {
411    format!("<div class='mech-string'>\"{}\"</div>", s)
412  } else if let Some(s) = (val as &dyn Any).downcast_ref::<bool>() {
413    format!("<div class='mech-boolean'>{}</div<", s)
414  } else {
415    format!("<div class='mech-number'>{}</div>", val)
416  }
417}
418
419impl<T> Matrix<T> 
420where T: Debug + Display + Clone + PartialEq + 'static + PrettyPrint
421{
422
423  pub fn to_html(&self) -> String {
424    let size = self.shape();
425    let mut html = String::new();
426    html.push_str("<table class='mech-matrix'>");
427    for i in 0..size[0] {
428      html.push_str("<tr>");
429      for j in 0..size[1] {
430        let value = self.index2d(i+1, j+1);
431        html.push_str(&format!("<td>{}</td>", quoted(&value)));
432      }
433      html.push_str("</tr>");
434    }
435    format!("<div class='mech-matrix-outer'><div class='mech-matrix-inner'></div>{}</div>", html)
436  }
437
438}
439
440impl<T> Matrix<T> 
441where T: Debug + Clone + PartialEq + 'static
442{
443
444  pub fn append(&mut self, other: &Matrix<T>) -> MResult<()> {
445    match (self, other) {
446      #[cfg(feature = "VectorD")]
447      (Matrix::DVector(lhs), Matrix::DVector(rhs)) => {
448        let mut lhs = lhs.borrow_mut();
449        let rhs = rhs.borrow();
450        let old_len = lhs.len();
451        lhs.resize_vertically_mut(old_len + rhs.len(), rhs[0].clone());
452        for (i, val) in rhs.iter().enumerate() {
453          lhs[old_len + i] = val.clone();
454        }
455        Ok(())
456      }
457      #[cfg(feature = "RowVectorD")]
458      (Matrix::RowDVector(lhs), Matrix::RowDVector(rhs)) => {
459        let mut lhs = lhs.borrow_mut();
460        let rhs = rhs.borrow();
461        let old_len = lhs.len();
462        lhs.resize_horizontally_mut(old_len + rhs.len(), rhs[0].clone());
463        for (i, val) in rhs.iter().enumerate() {
464          lhs[old_len + i] = val.clone();
465        }
466        Ok(())
467      }
468      _ => {
469        return Err(MechError{
470          id: line!(),
471          file: file!().to_string(),
472          tokens: vec![],
473          msg: "".to_string(),
474          kind: MechErrorKind::None,
475        });
476      }    
477    }
478  }
479
480  pub fn push(&mut self, value: T) -> MResult<()> {
481    match self {
482      #[cfg(feature = "RowVectorD")]
483      Matrix::RowDVector(vec) => {
484          let mut vec = vec.borrow_mut();
485          let new_len = vec.ncols() + 1;
486          vec.resize_horizontally_mut(new_len, value.clone()); // row vector: increase columns
487          Ok(())
488      }
489      #[cfg(feature = "VectorD")]
490      Matrix::DVector(vec) => {
491          let mut vec = vec.borrow_mut();
492          let new_len = vec.nrows() + 1;
493          vec.resize_vertically_mut(new_len, value.clone()); // column vector: increase rows
494          Ok(())
495      }
496      _ => {
497        return Err(MechError{
498          id: line!(),
499          file: file!().to_string(),
500          tokens: vec![],
501          msg: "".to_string(),
502          kind: MechErrorKind::None,
503        });
504      }
505    }
506  }
507
508  pub fn rows(&self) -> usize {
509    let size = self.shape();
510    size[0]
511  }
512
513  pub fn cols(&self) -> usize {
514    let size = self.shape();
515    size[1]
516  }
517
518  pub fn size_of(&self) -> usize {
519    let vec = self.as_vec();
520    vec.capacity() * size_of::<T>()
521  }       
522
523  pub fn resize_vertically(&mut self, new_size: usize, fill_value: T) -> MResult<()> {
524    match self {
525      #[cfg(feature = "RowVectorD")]
526      Matrix::RowDVector(vec) => {
527        let mut vec = vec.borrow_mut();
528        vec.resize_horizontally_mut(new_size, fill_value);
529        Ok(())
530      }
531      #[cfg(feature = "VectorD")]
532      Matrix::DVector(vec) => {
533        let mut vec = vec.borrow_mut();
534        vec.resize_vertically_mut(new_size, fill_value);
535        Ok(())
536      }
537      _ => {
538        return Err(MechError{
539          id: line!(),
540          file: file!().to_string(),
541          tokens: vec![],
542          msg: "".to_string(),
543          kind: MechErrorKind::None,
544        });
545      }
546    }
547  }
548
549  pub fn get_copyable_matrix(&self) -> Box<dyn CopyMat<T>> {
550    match self {
551      #[cfg(feature = "RowVector4")]
552      Matrix::RowVector4(ref x) => Box::new(x.clone()),
553      #[cfg(feature = "RowVector3")]
554      Matrix::RowVector3(ref x) => Box::new(x.clone()),
555      #[cfg(feature = "RowVector2")]
556      Matrix::RowVector2(ref x) => Box::new(x.clone()),
557      #[cfg(feature = "RowVectorD")]
558      Matrix::RowDVector(ref x) => Box::new(x.clone()),
559      #[cfg(feature = "Vector4")]
560      Matrix::Vector4(ref x) => Box::new(x.clone()),
561      #[cfg(feature = "Vector3")]
562      Matrix::Vector3(ref x) => Box::new(x.clone()),
563      #[cfg(feature = "Vector2")]
564      Matrix::Vector2(ref x) => Box::new(x.clone()),
565      #[cfg(feature = "VectorD")]
566      Matrix::DVector(ref x) => Box::new(x.clone()),
567      #[cfg(feature = "Matrix4")]
568      Matrix::Matrix4(ref x) => Box::new(x.clone()),
569      #[cfg(feature = "Matrix3")]
570      Matrix::Matrix3(ref x) => Box::new(x.clone()),
571      #[cfg(feature = "Matrix2")]
572      Matrix::Matrix2(ref x) => Box::new(x.clone()),
573      #[cfg(feature = "Matrix1")]
574      Matrix::Matrix1(ref x) => Box::new(x.clone()),
575      #[cfg(feature = "Matrix3x2")]
576      Matrix::Matrix3x2(ref x) => Box::new(x.clone()),
577      #[cfg(feature = "Matrix2x3")]
578      Matrix::Matrix2x3(ref x) => Box::new(x.clone()),
579      #[cfg(feature = "MatrixD")]
580      Matrix::DMatrix(ref x) => Box::new(x.clone()),
581    }
582  }
583
584  pub fn shape(&self) -> Vec<usize> {
585    let shape = match self {
586      #[cfg(feature = "RowVector4")]
587      Matrix::RowVector4(x) => x.borrow().shape(),
588      #[cfg(feature = "RowVector3")]
589      Matrix::RowVector3(x) => x.borrow().shape(),
590      #[cfg(feature = "RowVector2")]
591      Matrix::RowVector2(x) => x.borrow().shape(),
592      #[cfg(feature = "RowVectorD")]
593      Matrix::RowDVector(x) => x.borrow().shape(),
594      #[cfg(feature = "Vector4")]
595      Matrix::Vector4(x) => x.borrow().shape(),
596      #[cfg(feature = "Vector3")]
597      Matrix::Vector3(x) => x.borrow().shape(),
598      #[cfg(feature = "Vector2")]
599      Matrix::Vector2(x) => x.borrow().shape(),
600      #[cfg(feature = "VectorD")]
601      Matrix::DVector(x) => x.borrow().shape(),
602      #[cfg(feature = "Matrix4")]
603      Matrix::Matrix4(x) => x.borrow().shape(),
604      #[cfg(feature = "Matrix3")]
605      Matrix::Matrix3(x) => x.borrow().shape(),
606      #[cfg(feature = "Matrix2")]
607      Matrix::Matrix2(x) => x.borrow().shape(),
608      #[cfg(feature = "Matrix1")]
609      Matrix::Matrix1(x) => x.borrow().shape(),
610      #[cfg(feature = "Matrix3x2")]
611      Matrix::Matrix3x2(x) => x.borrow().shape(),
612      #[cfg(feature = "Matrix2x3")]
613      Matrix::Matrix2x3(x) => x.borrow().shape(),
614      #[cfg(feature = "MatrixD")]
615      Matrix::DMatrix(x) => x.borrow().shape(),
616    };
617    vec![shape.0, shape.1]
618  }
619
620  pub fn index1d(&self, ix: usize) -> T {
621    match self {
622      #[cfg(feature = "RowVector4")]
623      Matrix::RowVector4(x) => (*x.borrow().index(ix-1)).clone(),
624      #[cfg(feature = "RowVector3")]
625      Matrix::RowVector3(x) => (*x.borrow().index(ix-1)).clone(),
626      #[cfg(feature = "RowVector2")]
627      Matrix::RowVector2(x) => (*x.borrow().index(ix-1)).clone(),
628      #[cfg(feature = "RowVectorD")]
629      Matrix::RowDVector(x) => (*x.borrow().index(ix-1)).clone(),
630      #[cfg(feature = "Vector4")]
631      Matrix::Vector4(x) => (*x.borrow().index(ix-1)).clone(),
632      #[cfg(feature = "Vector3")]
633      Matrix::Vector3(x) => (*x.borrow().index(ix-1)).clone(),
634      #[cfg(feature = "Vector2")]
635      Matrix::Vector2(x) => (*x.borrow().index(ix-1)).clone(),
636      #[cfg(feature = "VectorD")]
637      Matrix::DVector(x) => (*x.borrow().index(ix-1)).clone(),
638      #[cfg(feature = "Matrix4")]
639      Matrix::Matrix4(x) => (*x.borrow().index(ix-1)).clone(),
640      #[cfg(feature = "Matrix3")]
641      Matrix::Matrix3(x) => (*x.borrow().index(ix-1)).clone(),
642      #[cfg(feature = "Matrix2")]
643      Matrix::Matrix2(x) => (*x.borrow().index(ix-1)).clone(),
644      #[cfg(feature = "Matrix1")]
645      Matrix::Matrix1(x) => (*x.borrow().index(ix-1)).clone(),
646      #[cfg(feature = "Matrix3x2")]
647      Matrix::Matrix3x2(x) => (*x.borrow().index(ix-1)).clone(),
648      #[cfg(feature = "Matrix2x3")]
649      Matrix::Matrix2x3(x) => (*x.borrow().index(ix-1)).clone(),
650      #[cfg(feature = "MatrixD")]
651      Matrix::DMatrix(x) => (*x.borrow().index(ix-1)).clone(),
652    }
653  }
654
655  pub fn set_index1d(&self, index: usize, value: T) {
656    match self {
657      #[cfg(feature = "RowVector4")]
658      Matrix::RowVector4(v) => v.borrow_mut()[index] = value,
659      #[cfg(feature = "RowVector3")]
660      Matrix::RowVector3(v) => v.borrow_mut()[index] = value,
661      #[cfg(feature = "RowVector2")]
662      Matrix::RowVector2(v) => v.borrow_mut()[index] = value,
663      #[cfg(feature = "RowVectorD")]
664      Matrix::RowDVector(v) => v.borrow_mut()[index] = value,
665      #[cfg(feature = "Vector4")]
666      Matrix::Vector4(v) => v.borrow_mut()[index] = value,
667      #[cfg(feature = "Vector3")]
668      Matrix::Vector3(v) => v.borrow_mut()[index] = value,
669      #[cfg(feature = "Vector2")]
670      Matrix::Vector2(v) => v.borrow_mut()[index] = value,
671      #[cfg(feature = "VectorD")]
672      Matrix::DVector(v) => v.borrow_mut()[index] = value,
673      #[cfg(feature = "Matrix1")]
674      Matrix::Matrix1(m) => m.borrow_mut()[index] = value,
675      #[cfg(feature = "Matrix2")]
676      Matrix::Matrix2(m) => m.borrow_mut()[index] = value,
677      #[cfg(feature = "Matrix3")]
678      Matrix::Matrix3(m) => m.borrow_mut()[index] = value,
679      #[cfg(feature = "Matrix4")]
680      Matrix::Matrix4(m) => m.borrow_mut()[index] = value,
681      #[cfg(feature = "Matrix2x3")]
682      Matrix::Matrix2x3(m) => m.borrow_mut()[index] = value,
683      #[cfg(feature = "Matrix3x2")]
684      Matrix::Matrix3x2(m) => m.borrow_mut()[index] = value,
685      #[cfg(feature = "MatrixD")]
686      Matrix::DMatrix(m) => m.borrow_mut()[index] = value,
687    }
688  }
689
690  pub fn set(&self, elements: Vec<T>) {
691    match self {
692      #[cfg(feature = "RowVector4")]
693      Matrix::RowVector4(x) => {
694        let mut x = x.borrow_mut();
695        x[0] = elements[0].clone();
696        x[1] = elements[1].clone();
697        x[2] = elements[2].clone();
698        x[3] = elements[3].clone();
699      }
700      #[cfg(feature = "RowVector3")]
701      Matrix::RowVector3(x) => {
702        let mut x = x.borrow_mut();
703        x[0] = elements[0].clone();
704        x[1] = elements[1].clone();
705        x[2] = elements[2].clone();
706      }
707      #[cfg(feature = "RowVector2")]
708      Matrix::RowVector2(x) => {
709        let mut x = x.borrow_mut();
710        x[0] = elements[0].clone();
711        x[1] = elements[1].clone();
712      }
713      #[cfg(feature = "RowVectorD")]
714      Matrix::RowDVector(x) => {let mut x = x.borrow_mut();for i in 0..elements.len() {x[i] = elements[i].clone();}},
715      #[cfg(feature = "Vector4")]
716      Matrix::Vector4(x) => {
717        let mut x = x.borrow_mut();
718        x[0] = elements[0].clone();
719        x[1] = elements[1].clone();
720        x[2] = elements[2].clone();
721        x[3] = elements[3].clone();
722      }
723      #[cfg(feature = "Vector3")]
724      Matrix::Vector3(x) => {
725        let mut x = x.borrow_mut();
726        x[0] = elements[0].clone();
727        x[1] = elements[1].clone();
728        x[2] = elements[2].clone();
729      }
730      #[cfg(feature = "Vector2")]
731      Matrix::Vector2(x) => {
732        let mut x = x.borrow_mut();
733        x[0] = elements[0].clone();
734        x[1] = elements[1].clone();
735      }
736      #[cfg(feature = "VectorD")]
737      Matrix::DVector(x) => {let mut x = x.borrow_mut();for i in 0..elements.len() {x[i] = elements[i].clone();}},
738      #[cfg(feature = "Matrix4")]
739      Matrix::Matrix4(x) => {
740        let mut x = x.borrow_mut();
741        x[0] = elements[0].clone();
742        x[1] = elements[1].clone();
743        x[2] = elements[2].clone();
744        x[3] = elements[3].clone();
745        x[4] = elements[4].clone();
746        x[5] = elements[5].clone();
747        x[6] = elements[6].clone();
748        x[7] = elements[7].clone();
749        x[8] = elements[8].clone();
750        x[9] = elements[9].clone();
751        x[10] = elements[10].clone();
752        x[11] = elements[11].clone();
753        x[12] = elements[12].clone();
754        x[13] = elements[13].clone();
755        x[14] = elements[14].clone();
756        x[15] = elements[15].clone();
757      }
758      #[cfg(feature = "Matrix3")]
759      Matrix::Matrix3(x) => {
760        let mut x = x.borrow_mut();
761        x[0] = elements[0].clone();
762        x[1] = elements[1].clone();
763        x[2] = elements[2].clone();
764        x[3] = elements[3].clone();
765        x[4] = elements[4].clone();
766        x[5] = elements[5].clone();
767        x[6] = elements[6].clone();
768        x[7] = elements[7].clone();
769        x[8] = elements[8].clone();
770      }
771      #[cfg(feature = "Matrix2")]
772      Matrix::Matrix2(x) => {
773        let mut x = x.borrow_mut();
774        x[0] = elements[0].clone();
775        x[1] = elements[1].clone();
776        x[2] = elements[2].clone();
777        x[3] = elements[3].clone();
778      }
779      #[cfg(feature = "Matrix1")]
780      Matrix::Matrix1(x) => {let mut x = x.borrow_mut();x[0] = elements[0].clone();},
781      #[cfg(feature = "Matrix3x2")]
782      Matrix::Matrix3x2(x) => {
783        let mut x = x.borrow_mut();
784        x[0] = elements[0].clone();
785        x[1] = elements[1].clone();
786        x[2] = elements[2].clone();
787        x[3] = elements[3].clone();
788        x[4] = elements[4].clone();
789        x[5] = elements[5].clone();
790      }
791      #[cfg(feature = "Matrix2x3")]
792      Matrix::Matrix2x3(x) => {
793        let mut x = x.borrow_mut();
794        x[0] = elements[0].clone();
795        x[1] = elements[1].clone();
796        x[2] = elements[2].clone();
797        x[3] = elements[3].clone();
798        x[4] = elements[4].clone();
799        x[5] = elements[5].clone();
800      }
801      #[cfg(feature = "MatrixD")]
802      Matrix::DMatrix(x) => {let mut x = x.borrow_mut();for i in 0..elements.len() {x[i] = elements[i].clone();}},
803    }
804  }
805
806  pub fn index2d(&self, row: usize, col: usize) -> T {
807    match self {
808      #[cfg(feature = "RowVector4")]
809      Matrix::RowVector4(x) => (*x.borrow().index((row-1,col-1))).clone(),
810      #[cfg(feature = "RowVector3")]
811      Matrix::RowVector3(x) => (*x.borrow().index((row-1,col-1))).clone(),
812      #[cfg(feature = "RowVector2")]
813      Matrix::RowVector2(x) => (*x.borrow().index((row-1,col-1))).clone(),
814      #[cfg(feature = "RowVectorD")]
815      Matrix::RowDVector(x) => (*x.borrow().index((row-1,col-1))).clone(),
816      #[cfg(feature = "Vector4")]
817      Matrix::Vector4(x) => (*x.borrow().index((row-1,col-1))).clone(),
818      #[cfg(feature = "Vector3")]
819      Matrix::Vector3(x) => (*x.borrow().index((row-1,col-1))).clone(),
820      #[cfg(feature = "Vector2")]
821      Matrix::Vector2(x) => (*x.borrow().index((row-1,col-1))).clone(),
822      #[cfg(feature = "VectorD")]
823      Matrix::DVector(x) => (*x.borrow().index((row-1,col-1))).clone(),
824      #[cfg(feature = "Matrix4")]
825      Matrix::Matrix4(x) => (*x.borrow().index((row-1,col-1))).clone(),
826      #[cfg(feature = "Matrix3")]
827      Matrix::Matrix3(x) => (*x.borrow().index((row-1,col-1))).clone(),
828      #[cfg(feature = "Matrix2")]
829      Matrix::Matrix2(x) => (*x.borrow().index((row-1,col-1))).clone(),
830      #[cfg(feature = "Matrix1")]
831      Matrix::Matrix1(x) => (*x.borrow().index((row-1,col-1))).clone(),
832      #[cfg(feature = "Matrix3x2")]
833      Matrix::Matrix3x2(x) => (*x.borrow().index((row-1,col-1))).clone(),
834      #[cfg(feature = "Matrix2x3")]
835      Matrix::Matrix2x3(x) => (*x.borrow().index((row-1,col-1))).clone(),
836      #[cfg(feature = "MatrixD")]
837      Matrix::DMatrix(x) => (*x.borrow().index((row-1,col-1))).clone(),
838    }
839  }
840
841  pub fn as_vec(&self) -> Vec<T> {
842    match self {
843      #[cfg(feature = "RowVector4")]
844      Matrix::RowVector4(x) => x.borrow().as_slice().to_vec(),
845      #[cfg(feature = "RowVector3")]
846      Matrix::RowVector3(x) => x.borrow().as_slice().to_vec(),
847      #[cfg(feature = "RowVector2")]
848      Matrix::RowVector2(x) => x.borrow().as_slice().to_vec(),
849      #[cfg(feature = "RowVectorD")]
850      Matrix::RowDVector(x) => x.borrow().as_slice().to_vec(),
851      #[cfg(feature = "Vector4")]
852      Matrix::Vector4(x) => x.borrow().as_slice().to_vec(),
853      #[cfg(feature = "Vector3")]
854      Matrix::Vector3(x) => x.borrow().as_slice().to_vec(),
855      #[cfg(feature = "Vector2")]
856      Matrix::Vector2(x) => x.borrow().as_slice().to_vec(),
857      #[cfg(feature = "VectorD")]
858      Matrix::DVector(x) => x.borrow().as_slice().to_vec(),
859      #[cfg(feature = "Matrix4")]
860      Matrix::Matrix4(x) => x.borrow().as_slice().to_vec(),
861      #[cfg(feature = "Matrix3")]
862      Matrix::Matrix3(x) => x.borrow().as_slice().to_vec(),
863      #[cfg(feature = "Matrix2")]
864      Matrix::Matrix2(x) => x.borrow().as_slice().to_vec(),
865      #[cfg(feature = "Matrix1")]
866      Matrix::Matrix1(x) => x.borrow().as_slice().to_vec(),
867      #[cfg(feature = "Matrix3x2")]
868      Matrix::Matrix3x2(x) => x.borrow().as_slice().to_vec(),
869      #[cfg(feature = "Matrix2x3")]
870      Matrix::Matrix2x3(x) => x.borrow().as_slice().to_vec(),
871      #[cfg(feature = "MatrixD")]
872      Matrix::DMatrix(x) => x.borrow().as_slice().to_vec(),
873    }
874  }
875
876}
877
878macro_rules! impl_to_value_for_matrix {
879  ($t:ty, $variant:ident) => {
880    impl ToValue for Matrix<$t> {
881      fn to_value(&self) -> Value {
882        Value::$variant(self.clone())
883      }
884    }
885  };
886}
887
888impl_to_value_for_matrix!(Value, MatrixValue);
889impl_to_value_for_matrix!(F64, MatrixF64);
890impl_to_value_for_matrix!(F32, MatrixF32);
891impl_to_value_for_matrix!(i8, MatrixI8);
892impl_to_value_for_matrix!(i16, MatrixI16);
893impl_to_value_for_matrix!(i32, MatrixI32);
894impl_to_value_for_matrix!(i64, MatrixI64);
895impl_to_value_for_matrix!(i128, MatrixI128);
896impl_to_value_for_matrix!(u8, MatrixU8);
897impl_to_value_for_matrix!(u16, MatrixU16);
898impl_to_value_for_matrix!(u32, MatrixU32);
899impl_to_value_for_matrix!(u64, MatrixU64);
900impl_to_value_for_matrix!(u128, MatrixU128);
901impl_to_value_for_matrix!(bool, MatrixBool);
902impl_to_value_for_matrix!(String, MatrixString);
903impl_to_value_for_matrix!(ComplexNumber, MatrixComplexNumber);
904impl_to_value_for_matrix!(RationalNumber, MatrixRationalNumber);