1#[cfg(test)]
2use super::super::test::ErrorTensor;
3
4use crate::math::{
5 Jacobian, Solution, Tensor, TensorArray, TensorRank0, TensorRank1, TensorRank2,
6 TensorRank2Vec2D, TensorVec, Vector, write_tensor_rank_0,
7};
8use std::{
9 fmt::{self, Display, Formatter},
10 mem::transmute,
11 ops::{Add, AddAssign, Div, DivAssign, Index, IndexMut, Mul, MulAssign, Sub, SubAssign},
12};
13
14#[derive(Clone, Debug)]
18pub struct TensorRank1Vec<const D: usize, const I: usize>(Vec<TensorRank1<D, I>>);
19
20impl<const D: usize, const I: usize> Display for TensorRank1Vec<D, I> {
21 fn fmt(&self, f: &mut Formatter) -> fmt::Result {
22 write!(f, "\x1B[s")?;
23 write!(f, "[[")?;
24 self.iter().enumerate().try_for_each(|(i, tensor_rank_1)| {
25 tensor_rank_1
26 .iter()
27 .try_for_each(|entry| write_tensor_rank_0(f, entry))?;
28 if i + 1 < self.len() {
29 writeln!(f, "\x1B[2D],")?;
30 write!(f, "\x1B[u")?;
31 write!(f, "\x1B[{}B [", i + 1)?;
32 }
33 Ok(())
34 })?;
35 write!(f, "\x1B[2D]]")
36 }
37}
38
39#[cfg(test)]
40impl<const D: usize, const I: usize> ErrorTensor for TensorRank1Vec<D, I> {
41 fn error_fd(&self, comparator: &Self, epsilon: &TensorRank0) -> Option<(bool, usize)> {
42 let error_count = self
43 .iter()
44 .zip(comparator.iter())
45 .map(|(entry, comparator_entry)| {
46 entry
47 .iter()
48 .zip(comparator_entry.iter())
49 .filter(|&(&entry_i, &comparator_entry_i)| {
50 &(entry_i / comparator_entry_i - 1.0).abs() >= epsilon
51 && (&entry_i.abs() >= epsilon || &comparator_entry_i.abs() >= epsilon)
52 })
53 .count()
54 })
55 .sum();
56 if error_count > 0 {
57 let auxiliary = self
58 .iter()
59 .zip(comparator.iter())
60 .map(|(entry, comparator_entry)| {
61 entry
62 .iter()
63 .zip(comparator_entry.iter())
64 .filter(|&(&entry_i, &comparator_entry_i)| {
65 &(entry_i / comparator_entry_i - 1.0).abs() >= epsilon
66 && &(entry_i - comparator_entry_i).abs() >= epsilon
67 && (&entry_i.abs() >= epsilon
68 || &comparator_entry_i.abs() >= epsilon)
69 })
70 .count()
71 })
72 .sum::<usize>()
73 > 0;
74 Some((auxiliary, error_count))
75 } else {
76 None
77 }
78 }
79}
80
81impl<const D: usize, const I: usize> From<Vec<[TensorRank0; D]>> for TensorRank1Vec<D, I> {
82 fn from(vec: Vec<[TensorRank0; D]>) -> Self {
83 vec.into_iter()
84 .map(|tensor_rank_1| tensor_rank_1.into())
85 .collect()
86 }
87}
88
89impl<const D: usize, const I: usize> From<Vec<Vec<TensorRank0>>> for TensorRank1Vec<D, I> {
90 fn from(vec: Vec<Vec<TensorRank0>>) -> Self {
91 vec.into_iter()
92 .map(|tensor_rank_1| tensor_rank_1.into())
93 .collect()
94 }
95}
96
97impl<const D: usize, const I: usize> From<TensorRank1Vec<D, I>> for Vec<[TensorRank0; D]> {
98 fn from(tensor_rank_1_vec: TensorRank1Vec<D, I>) -> Self {
99 tensor_rank_1_vec
100 .iter()
101 .map(|tensor_rank_1| tensor_rank_1.clone().into())
102 .collect()
103 }
104}
105
106impl<const D: usize, const I: usize> From<TensorRank1Vec<D, I>> for Vec<Vec<TensorRank0>> {
107 fn from(tensor_rank_1_vec: TensorRank1Vec<D, I>) -> Self {
108 tensor_rank_1_vec
109 .iter()
110 .map(|tensor_rank_1| tensor_rank_1.clone().into())
111 .collect()
112 }
113}
114
115impl From<TensorRank1Vec<3, 0>> for TensorRank1Vec<3, 1> {
116 fn from(tensor_rank_1_vec: TensorRank1Vec<3, 0>) -> Self {
117 unsafe { transmute::<TensorRank1Vec<3, 0>, TensorRank1Vec<3, 1>>(tensor_rank_1_vec) }
118 }
119}
120
121impl From<TensorRank1Vec<3, 1>> for TensorRank1Vec<3, 0> {
122 fn from(tensor_rank_1_vec: TensorRank1Vec<3, 1>) -> Self {
123 unsafe { transmute::<TensorRank1Vec<3, 1>, TensorRank1Vec<3, 0>>(tensor_rank_1_vec) }
124 }
125}
126
127impl<const D: usize, const I: usize> From<Vector> for TensorRank1Vec<D, I> {
128 fn from(vector: Vector) -> Self {
129 let n = vector.len();
130 if n % D != 0 {
131 panic!("Vector length mismatch.")
132 } else {
133 (0..n / D)
134 .map(|a| (0..D).map(|i| vector[D * a + i]).collect())
135 .collect()
136 }
137 }
138}
139
140impl<const D: usize, const I: usize> From<&Vector> for TensorRank1Vec<D, I> {
141 fn from(vector: &Vector) -> Self {
142 let n = vector.len();
143 if n % D != 0 {
144 panic!("Vector length mismatch.")
145 } else {
146 (0..n / D)
147 .map(|a| (0..D).map(|i| vector[D * a + i]).collect())
148 .collect()
149 }
150 }
151}
152
153impl<const D: usize, const I: usize> FromIterator<TensorRank1<D, I>> for TensorRank1Vec<D, I> {
154 fn from_iter<Ii: IntoIterator<Item = TensorRank1<D, I>>>(into_iterator: Ii) -> Self {
155 Self(Vec::from_iter(into_iterator))
156 }
157}
158
159impl<const D: usize, const I: usize> Index<usize> for TensorRank1Vec<D, I> {
160 type Output = TensorRank1<D, I>;
161 fn index(&self, index: usize) -> &Self::Output {
162 &self.0[index]
163 }
164}
165
166impl<const D: usize, const I: usize> IndexMut<usize> for TensorRank1Vec<D, I> {
167 fn index_mut(&mut self, index: usize) -> &mut Self::Output {
168 &mut self.0[index]
169 }
170}
171
172impl<const D: usize, const I: usize> TensorRank1Vec<D, I> {
173 pub fn dot(&self, tensors: &Self) -> TensorRank0 {
175 self.iter()
176 .zip(tensors.iter())
177 .map(|(entry, tensor)| entry * tensor)
178 .sum()
179 }
180}
181
182impl<const D: usize, const I: usize> TensorVec for TensorRank1Vec<D, I> {
183 type Item = TensorRank1<D, I>;
184 type Slice<'a> = &'a [[TensorRank0; D]];
185 fn append(&mut self, other: &mut Self) {
186 self.0.append(&mut other.0)
187 }
188 fn is_empty(&self) -> bool {
189 self.0.is_empty()
190 }
191 fn len(&self) -> usize {
192 self.0.len()
193 }
194 fn new(slice: Self::Slice<'_>) -> Self {
195 slice
196 .iter()
197 .map(|slice_entry| Self::Item::new(*slice_entry))
198 .collect()
199 }
200 fn push(&mut self, item: Self::Item) {
201 self.0.push(item)
202 }
203 fn remove(&mut self, index: usize) -> Self::Item {
204 self.0.remove(index)
205 }
206 fn retain<F>(&mut self, f: F)
207 where
208 F: FnMut(&Self::Item) -> bool,
209 {
210 self.0.retain(f)
211 }
212 fn swap_remove(&mut self, index: usize) -> Self::Item {
213 self.0.swap_remove(index)
214 }
215 fn zero(len: usize) -> Self {
216 (0..len).map(|_| super::zero()).collect()
217 }
218}
219
220impl<const D: usize, const I: usize> Tensor for TensorRank1Vec<D, I> {
221 type Item = TensorRank1<D, I>;
222 fn iter(&self) -> impl Iterator<Item = &Self::Item> {
223 self.0.iter()
224 }
225 fn iter_mut(&mut self) -> impl Iterator<Item = &mut Self::Item> {
226 self.0.iter_mut()
227 }
228 fn norm_inf(&self) -> TensorRank0 {
229 self.iter()
230 .map(|tensor_rank_1| {
231 tensor_rank_1
232 .iter()
233 .fold(0.0, |acc, entry| entry.abs().max(acc))
234 })
235 .reduce(TensorRank0::max)
236 .unwrap()
237 }
238 fn num_entries(&self) -> usize {
239 D * self.len()
240 }
241}
242
243impl<const D: usize, const I: usize> IntoIterator for TensorRank1Vec<D, I> {
244 type Item = TensorRank1<D, I>;
245 type IntoIter = std::vec::IntoIter<Self::Item>;
246 fn into_iter(self) -> Self::IntoIter {
247 self.0.into_iter()
248 }
249}
250
251impl<const D: usize, const I: usize> Solution for TensorRank1Vec<D, I> {
252 fn decrement_from_chained(&mut self, other: &mut Vector, vector: Vector) {
253 self.iter_mut()
254 .flat_map(|x| x.iter_mut())
255 .chain(other.iter_mut())
256 .zip(vector)
257 .for_each(|(entry_i, vector_i)| *entry_i -= vector_i)
258 }
259}
260
261impl<const D: usize, const I: usize> Jacobian for TensorRank1Vec<D, I> {
262 fn fill_into(self, vector: &mut Vector) {
263 self.into_iter()
264 .flatten()
265 .zip(vector.iter_mut())
266 .for_each(|(self_i, vector_i)| *vector_i = self_i)
267 }
268 fn fill_into_chained(self, other: Vector, vector: &mut Vector) {
269 self.into_iter()
270 .flatten()
271 .chain(other)
272 .zip(vector.iter_mut())
273 .for_each(|(self_i, vector_i)| *vector_i = self_i)
274 }
275}
276
277impl<const D: usize, const I: usize, const J: usize> Div<TensorRank2Vec2D<D, I, J>>
278 for &TensorRank1Vec<D, I>
279{
280 type Output = TensorRank1Vec<D, J>;
281 fn div(self, _tensor_rank_2_vec_2d: TensorRank2Vec2D<D, I, J>) -> Self::Output {
282 todo!()
283 }
284}
285
286impl<const D: usize, const I: usize> Sub<Vector> for TensorRank1Vec<D, I> {
287 type Output = Self;
288 fn sub(mut self, vector: Vector) -> Self::Output {
289 self.iter_mut().enumerate().for_each(|(a, self_a)| {
290 self_a
291 .iter_mut()
292 .enumerate()
293 .for_each(|(i, self_a_i)| *self_a_i -= vector[D * a + i])
294 });
295 self
296 }
297}
298
299impl<const D: usize, const I: usize> Sub<&Vector> for TensorRank1Vec<D, I> {
300 type Output = Self;
301 fn sub(mut self, vector: &Vector) -> Self::Output {
302 self.iter_mut().enumerate().for_each(|(a, self_a)| {
303 self_a
304 .iter_mut()
305 .enumerate()
306 .for_each(|(i, self_a_i)| *self_a_i -= vector[D * a + i])
307 });
308 self
309 }
310}
311
312impl<const D: usize, const I: usize> Div<TensorRank0> for TensorRank1Vec<D, I> {
313 type Output = Self;
314 fn div(mut self, tensor_rank_0: TensorRank0) -> Self::Output {
315 self /= &tensor_rank_0;
316 self
317 }
318}
319
320impl<const D: usize, const I: usize> Div<&TensorRank0> for TensorRank1Vec<D, I> {
321 type Output = Self;
322 fn div(mut self, tensor_rank_0: &TensorRank0) -> Self::Output {
323 self /= tensor_rank_0;
324 self
325 }
326}
327
328impl<const D: usize, const I: usize> DivAssign<TensorRank0> for TensorRank1Vec<D, I> {
329 fn div_assign(&mut self, tensor_rank_0: TensorRank0) {
330 self.iter_mut().for_each(|entry| *entry /= &tensor_rank_0);
331 }
332}
333
334impl<const D: usize, const I: usize> DivAssign<&TensorRank0> for TensorRank1Vec<D, I> {
335 fn div_assign(&mut self, tensor_rank_0: &TensorRank0) {
336 self.iter_mut().for_each(|entry| *entry /= tensor_rank_0);
337 }
338}
339
340impl<const D: usize, const I: usize> Mul<TensorRank0> for TensorRank1Vec<D, I> {
341 type Output = Self;
342 fn mul(mut self, tensor_rank_0: TensorRank0) -> Self::Output {
343 self *= &tensor_rank_0;
344 self
345 }
346}
347
348impl<const D: usize, const I: usize> Mul<&TensorRank0> for TensorRank1Vec<D, I> {
349 type Output = Self;
350 fn mul(mut self, tensor_rank_0: &TensorRank0) -> Self::Output {
351 self *= tensor_rank_0;
352 self
353 }
354}
355
356impl<const D: usize, const I: usize> Mul<TensorRank0> for &TensorRank1Vec<D, I> {
357 type Output = TensorRank1Vec<D, I>;
358 fn mul(self, tensor_rank_0: TensorRank0) -> Self::Output {
359 self.iter().map(|self_i| self_i * tensor_rank_0).collect()
360 }
361}
362
363impl<const D: usize, const I: usize> Mul<&TensorRank0> for &TensorRank1Vec<D, I> {
364 type Output = TensorRank1Vec<D, I>;
365 fn mul(self, tensor_rank_0: &TensorRank0) -> Self::Output {
366 self.iter().map(|self_i| self_i * tensor_rank_0).collect()
367 }
368}
369
370impl<const D: usize, const I: usize> MulAssign<TensorRank0> for TensorRank1Vec<D, I> {
371 fn mul_assign(&mut self, tensor_rank_0: TensorRank0) {
372 self.iter_mut().for_each(|entry| *entry *= &tensor_rank_0);
373 }
374}
375
376impl<const D: usize, const I: usize> MulAssign<&TensorRank0> for TensorRank1Vec<D, I> {
377 fn mul_assign(&mut self, tensor_rank_0: &TensorRank0) {
378 self.iter_mut().for_each(|entry| *entry *= tensor_rank_0);
379 }
380}
381
382impl<const D: usize, const I: usize> Add for TensorRank1Vec<D, I> {
383 type Output = Self;
384 fn add(mut self, tensor_rank_1_vec: Self) -> Self::Output {
385 self += tensor_rank_1_vec;
386 self
387 }
388}
389
390impl<const D: usize, const I: usize> Add<&Self> for TensorRank1Vec<D, I> {
391 type Output = Self;
392 fn add(mut self, tensor_rank_1_vec: &Self) -> Self::Output {
393 self += tensor_rank_1_vec;
394 self
395 }
396}
397
398impl<const D: usize, const I: usize> AddAssign for TensorRank1Vec<D, I> {
399 fn add_assign(&mut self, tensor_rank_1_vec: Self) {
400 self.iter_mut()
401 .zip(tensor_rank_1_vec.iter())
402 .for_each(|(self_entry, tensor_rank_1)| *self_entry += tensor_rank_1);
403 }
404}
405
406impl<const D: usize, const I: usize> AddAssign<&Self> for TensorRank1Vec<D, I> {
407 fn add_assign(&mut self, tensor_rank_1_vec: &Self) {
408 self.iter_mut()
409 .zip(tensor_rank_1_vec.iter())
410 .for_each(|(self_entry, tensor_rank_1)| *self_entry += tensor_rank_1);
411 }
412}
413
414impl<const D: usize, const I: usize, const J: usize> Mul<TensorRank1Vec<D, J>>
415 for TensorRank1Vec<D, I>
416{
417 type Output = TensorRank2<D, I, J>;
418 fn mul(self, tensor_rank_1_vec: TensorRank1Vec<D, J>) -> Self::Output {
419 self.iter()
420 .zip(tensor_rank_1_vec.iter())
421 .map(|(self_entry, tensor_rank_1_vec_entry)| {
422 TensorRank2::dyad(self_entry, tensor_rank_1_vec_entry)
423 })
424 .sum()
425 }
426}
427
428impl<const D: usize, const I: usize, const J: usize> Mul<&TensorRank1Vec<D, J>>
429 for TensorRank1Vec<D, I>
430{
431 type Output = TensorRank2<D, I, J>;
432 fn mul(self, tensor_rank_1_vec: &TensorRank1Vec<D, J>) -> Self::Output {
433 self.iter()
434 .zip(tensor_rank_1_vec.iter())
435 .map(|(self_entry, tensor_rank_1_vec_entry)| {
436 TensorRank2::dyad(self_entry, tensor_rank_1_vec_entry)
437 })
438 .sum()
439 }
440}
441
442impl<const D: usize, const I: usize, const J: usize> Mul<TensorRank1Vec<D, J>>
443 for &TensorRank1Vec<D, I>
444{
445 type Output = TensorRank2<D, I, J>;
446 fn mul(self, tensor_rank_1_vec: TensorRank1Vec<D, J>) -> Self::Output {
447 self.iter()
448 .zip(tensor_rank_1_vec.iter())
449 .map(|(self_entry, tensor_rank_1_vec_entry)| {
450 TensorRank2::dyad(self_entry, tensor_rank_1_vec_entry)
451 })
452 .sum()
453 }
454}
455
456impl<const D: usize, const I: usize, const J: usize> Mul<&TensorRank1Vec<D, J>>
457 for &TensorRank1Vec<D, I>
458{
459 type Output = TensorRank2<D, I, J>;
460 fn mul(self, tensor_rank_1_vec: &TensorRank1Vec<D, J>) -> Self::Output {
461 self.iter()
462 .zip(tensor_rank_1_vec.iter())
463 .map(|(self_entry, tensor_rank_1_vec_entry)| {
464 TensorRank2::dyad(self_entry, tensor_rank_1_vec_entry)
465 })
466 .sum()
467 }
468}
469
470impl<const D: usize, const I: usize> Sub for TensorRank1Vec<D, I> {
471 type Output = Self;
472 fn sub(mut self, tensor_rank_1_vec: Self) -> Self::Output {
473 self -= tensor_rank_1_vec;
474 self
475 }
476}
477
478impl<const D: usize, const I: usize> Sub<&Self> for TensorRank1Vec<D, I> {
479 type Output = Self;
480 fn sub(mut self, tensor_rank_1_vec: &Self) -> Self::Output {
481 self -= tensor_rank_1_vec;
482 self
483 }
484}
485
486impl<const D: usize, const I: usize> Sub for &TensorRank1Vec<D, I> {
487 type Output = TensorRank1Vec<D, I>;
488 fn sub(self, tensor_rank_1_vec: Self) -> Self::Output {
489 tensor_rank_1_vec
490 .iter()
491 .zip(self.iter())
492 .map(|(tensor_rank_1_vec_a, self_a)| {
493 tensor_rank_1_vec_a
494 .iter()
495 .zip(self_a.iter())
496 .map(|(tensor_rank_1_vec_a_i, self_a_i)| self_a_i - *tensor_rank_1_vec_a_i)
497 .collect()
498 })
499 .collect()
500 }
501}
502
503impl<const D: usize, const I: usize> SubAssign for TensorRank1Vec<D, I> {
504 fn sub_assign(&mut self, tensor_rank_1_vec: Self) {
505 self.iter_mut()
506 .zip(tensor_rank_1_vec.iter())
507 .for_each(|(self_entry, tensor_rank_1)| *self_entry -= tensor_rank_1);
508 }
509}
510
511impl<const D: usize, const I: usize> SubAssign<&Self> for TensorRank1Vec<D, I> {
512 fn sub_assign(&mut self, tensor_rank_1_vec: &Self) {
513 self.iter_mut()
514 .zip(tensor_rank_1_vec.iter())
515 .for_each(|(self_entry, tensor_rank_1)| *self_entry -= tensor_rank_1);
516 }
517}