1use crate::errors::Error;
24use cpython::{exc, PyErr, PyResult, Python};
25
26pub struct Vectors {
27 input_vector1: Vec<f64>,
28 input_vector2: Vec<f64>,
29}
30
31impl Vectors {
32 pub fn new(input_vector1: Vec<f64>, input_vector2: Vec<f64>) -> Result<Self, Error> {
33 if input_vector1.len() != input_vector2.len() {
34 return Err(Error::InvalidParams(String::from(
35 "Vectors length mismatch",
36 )));
37 }
38 Ok(Self {
39 input_vector1,
40 input_vector2,
41 })
42 }
43
44 pub fn add(&self) -> Vec<f64> {
46 let mut output_vector = Vec::new();
47 for idx in 0..self.input_vector1.len() {
48 output_vector.push(self.input_vector1[idx] + self.input_vector2[idx])
49 }
50 output_vector
51 }
52
53 pub fn sub(&self) -> Vec<f64> {
55 let mut output_vector = Vec::new();
56 for idx in 0..self.input_vector1.len() {
57 output_vector.push(self.input_vector1[idx] - self.input_vector2[idx])
58 }
59 output_vector
60 }
61 pub fn div(&self) -> Vec<f64> {
63 let mut output_vector = Vec::new();
64 for idx in 0..self.input_vector1.len() {
65 output_vector.push(self.input_vector1[idx] / self.input_vector2[idx])
66 }
67 output_vector
68 }
69 pub fn mul(&self) -> Vec<f64> {
71 let mut output_vector = Vec::new();
72 for idx in 0..self.input_vector1.len() {
73 output_vector.push(self.input_vector1[idx] * self.input_vector2[idx])
74 }
75 output_vector
76 }
77}
78
79pub fn add_py(py: Python, vector1: Vec<f64>, vector2: Vec<f64>) -> PyResult<Vec<f64>> {
80 let vec_zip = Vectors::new(vector1, vector2);
81 let vectors = match vec_zip {
82 Ok(x) => x,
83 Err(err_typ) => match err_typ {
84 Error::InvalidParams(msg) => return Err(PyErr::new::<exc::IndexError, _>(py, msg)),
85 },
86 };
87 let out_vec = vectors.add();
88 Ok(out_vec)
89}
90
91pub fn sub_py(py: Python, vector1: Vec<f64>, vector2: Vec<f64>) -> PyResult<Vec<f64>> {
92 let vec_zip = Vectors::new(vector1, vector2);
93 let vectors = match vec_zip {
94 Ok(x) => x,
95 Err(err_typ) => match err_typ {
96 Error::InvalidParams(msg) => return Err(PyErr::new::<exc::IndexError, _>(py, msg)),
97 },
98 };
99 let out_vec = vectors.sub();
100 Ok(out_vec)
101}
102
103pub fn mul_py(py: Python, vector1: Vec<f64>, vector2: Vec<f64>) -> PyResult<Vec<f64>> {
104 let vec_zip = Vectors::new(vector1, vector2);
105 let vectors = match vec_zip {
106 Ok(x) => x,
107 Err(err_typ) => match err_typ {
108 Error::InvalidParams(msg) => return Err(PyErr::new::<exc::IndexError, _>(py, msg)),
109 },
110 };
111 let out_vec = vectors.mul();
112 Ok(out_vec)
113}
114
115pub fn div_py(py: Python, vector1: Vec<f64>, vector2: Vec<f64>) -> PyResult<Vec<f64>> {
116 let vec_zip = Vectors::new(vector1, vector2);
117 let vectors = match vec_zip {
118 Ok(x) => x,
119 Err(err_typ) => match err_typ {
120 Error::InvalidParams(msg) => return Err(PyErr::new::<exc::IndexError, _>(py, msg)),
121 },
122 };
123 let out_vec = vectors.div();
124 Ok(out_vec)
125}
126
127#[cfg(test)]
135mod test {
136 use super::*;
137
138 #[test]
139 fn test_vect_mul() {
140 let vec1 = vec![1.0, 2.0, 3.0, 4.0];
141 let vec2 = vec![1.0, 2.0, 3.0, 4.0];
142 let vectors = Vectors::new(vec1, vec2).unwrap();
143 let vec_mul = vectors.mul();
144
145 assert_eq!(vec_mul, vec![1.0, 4.0, 9.0, 16.0])
146 }
147 #[test]
148 fn test_vect_add() {
149 let vec1 = vec![1.0, 2.0, 3.0, 4.0];
150 let vec2 = vec![1.0, 2.0, 3.0, 4.0];
151
152 let vectors = Vectors::new(vec1, vec2).unwrap();
153 let vec_add = vectors.add();
154
155 assert_eq!(vec_add, vec![2.0, 4.0, 6.0, 8.0])
156 }
157 #[test]
158 fn test_vect_div() {
159 let vec1 = vec![1.0, 2.0, 3.0, 4.0];
160 let vec2 = vec![1.0, 2.0, 3.0, 4.0];
161
162 let vectors = Vectors::new(vec1, vec2).unwrap();
163 let vec_div = vectors.div();
164
165 assert_eq!(vec_div, vec![1.0, 1.0, 1.0, 1.0])
166 }
167 #[test]
168 fn test_vect_sub() {
169 let vec1 = vec![1.0, 2.0, 3.0, 4.0];
170 let vec2 = vec![1.0, 2.0, 3.0, 4.0];
171
172 let vectors = Vectors::new(vec1, vec2).unwrap();
173 let vec_sub = vectors.sub();
174
175 assert_eq!(vec_sub, vec![0.0, 0.0, 0.0, 0.0])
176 }
177}