opensrdk_linear_algebra/matrix/ge/operators/
add.rs1use crate::matrix::ge::Matrix;
2use crate::number::{c64, Number};
3use rayon::prelude::*;
4use std::ops::{Add, AddAssign};
5
6fn add_scalar<T>(lhs: T, rhs: Matrix<T>) -> Matrix<T>
7where
8 T: Number,
9{
10 let mut rhs = rhs;
11
12 rhs.elems
13 .par_iter_mut()
14 .map(|r| {
15 *r += lhs;
16 })
17 .collect::<Vec<_>>();
18
19 rhs
20}
21
22fn add<T>(lhs: Matrix<T>, rhs: &Matrix<T>) -> Matrix<T>
23where
24 T: Number,
25{
26 if !lhs.is_same_size(rhs) {
27 panic!("Dimension mismatch.")
28 }
29 let mut lhs = lhs;
30
31 lhs.elems
32 .par_iter_mut()
33 .zip(rhs.elems.par_iter())
34 .map(|(l, &r)| {
35 *l += r;
36 })
37 .collect::<Vec<_>>();
38
39 lhs
40}
41
42macro_rules! impl_div_scalar {
45 {$t: ty} => {
46 impl Add<Matrix<$t>> for $t {
47 type Output = Matrix<$t>;
48
49 fn add(self, rhs: Matrix<$t>) -> Self::Output {
50 add_scalar(self, rhs)
51 }
52 }
53
54 impl Add<Matrix<$t>> for &$t {
55 type Output = Matrix<$t>;
56
57 fn add(self, rhs: Matrix<$t>) -> Self::Output {
58 add_scalar(*self, rhs)
59 }
60 }
61 }
62}
63
64impl_div_scalar! {f64}
65impl_div_scalar! {c64}
66
67impl<T> Add<T> for Matrix<T>
70where
71 T: Number,
72{
73 type Output = Matrix<T>;
74
75 fn add(self, rhs: T) -> Self::Output {
76 add_scalar(rhs, self)
77 }
78}
79
80impl<T> Add<&T> for Matrix<T>
81where
82 T: Number,
83{
84 type Output = Matrix<T>;
85
86 fn add(self, rhs: &T) -> Self::Output {
87 add_scalar(*rhs, self)
88 }
89}
90
91impl<T> Add<Matrix<T>> for Matrix<T>
94where
95 T: Number,
96{
97 type Output = Matrix<T>;
98
99 fn add(self, rhs: Matrix<T>) -> Self::Output {
100 add(self, &rhs)
101 }
102}
103
104impl<T> Add<&Matrix<T>> for Matrix<T>
105where
106 T: Number,
107{
108 type Output = Matrix<T>;
109
110 fn add(self, rhs: &Matrix<T>) -> Self::Output {
111 add(self, rhs)
112 }
113}
114
115impl<T> Add<Matrix<T>> for &Matrix<T>
116where
117 T: Number,
118{
119 type Output = Matrix<T>;
120
121 fn add(self, rhs: Matrix<T>) -> Self::Output {
122 add(rhs, self)
123 }
124}
125
126impl<T> AddAssign<Matrix<T>> for Matrix<T>
129where
130 T: Number,
131{
132 fn add_assign(&mut self, rhs: Matrix<T>) {
133 *self = self as &Self + rhs;
134 }
135}
136
137#[cfg(test)]
138mod tests {
139 use crate::*;
140 #[test]
141 fn it_works() {
142 let a = mat!(
143 1.0, 2.0;
144 3.0, 4.0
145 ) + mat!(
146 5.0, 6.0;
147 7.0, 8.0
148 );
149 assert_eq!(a[(0, 0)], 6.0);
150 assert_eq!(a[(0, 1)], 8.0);
151 assert_eq!(a[(1, 0)], 10.0);
152 assert_eq!(a[(1, 1)], 12.0);
153 }
154}