simba/simd/
simd_complex.rs1use num::{NumAssignOps, NumOps, Zero};
2use std::any::Any;
3use std::f64;
4use std::fmt::Debug;
5use std::ops::Neg;
6
7use crate::scalar::{ComplexField, Field, SubsetOf, SupersetOf};
8use crate::simd::{SimdRealField, SimdValue};
9
10#[allow(missing_docs)]
14pub trait SimdComplexField:
15SubsetOf<Self>
16+ SupersetOf<f32>
17+ SupersetOf<f64>
18+ Field
19+ Clone
20+ Neg<Output=Self>
21+ Send
24+ Sync
25+ Any
26+ 'static
27+ Debug
28+ NumAssignOps
29+ NumOps
30+ PartialEq
31{
32 type SimdRealField: SimdRealField<SimdBool=<Self as SimdValue>::SimdBool>;
34 fn from_simd_real(re: Self::SimdRealField) -> Self;
36
37 fn simd_real(self) -> Self::SimdRealField;
39
40 fn simd_imaginary(self) -> Self::SimdRealField;
42
43 fn simd_modulus(self) -> Self::SimdRealField;
45
46 fn simd_modulus_squared(self) -> Self::SimdRealField;
48
49 fn simd_argument(self) -> Self::SimdRealField;
51
52 fn simd_norm1(self) -> Self::SimdRealField;
54
55 fn simd_scale(self, factor: Self::SimdRealField) -> Self;
57
58 fn simd_unscale(self, factor: Self::SimdRealField) -> Self;
60
61 fn simd_to_polar(self) -> (Self::SimdRealField, Self::SimdRealField) {
63 (self.clone().simd_modulus(), self.simd_argument())
64 }
65
66 fn simd_to_exp(self) -> (Self::SimdRealField, Self) {
68 let m = self.clone().simd_modulus();
69
70 if !m.is_zero() {
71 (m.clone(), self.simd_unscale(m))
72 } else {
73 (Self::SimdRealField::zero(), Self::one())
74 }
75 }
76
77 fn simd_signum(self) -> Self {
79 self.simd_to_exp().1
80 }
81
82 fn simd_floor(self) -> Self;
83 fn simd_ceil(self) -> Self;
84 fn simd_round(self) -> Self;
85 fn simd_trunc(self) -> Self;
86 fn simd_fract(self) -> Self;
87 fn simd_mul_add(self, a: Self, b: Self) -> Self;
88
89 fn simd_abs(self) -> Self::SimdRealField;
93
94 fn simd_hypot(self, other: Self) -> Self::SimdRealField;
96
97 fn simd_recip(self) -> Self;
98 fn simd_conjugate(self) -> Self;
99 fn simd_sin(self) -> Self;
100 fn simd_cos(self) -> Self;
101 fn simd_sin_cos(self) -> (Self, Self);
102 #[inline]
103 fn simd_sinh_cosh(self) -> (Self, Self) {
104 (self.clone().simd_sinh(), self.simd_cosh())
105 }
106 fn simd_tan(self) -> Self;
107 fn simd_asin(self) -> Self;
108 fn simd_acos(self) -> Self;
109 fn simd_atan(self) -> Self;
110 fn simd_sinh(self) -> Self;
111 fn simd_cosh(self) -> Self;
112 fn simd_tanh(self) -> Self;
113 fn simd_asinh(self) -> Self;
114 fn simd_acosh(self) -> Self;
115 fn simd_atanh(self) -> Self;
116
117 #[inline]
119 fn simd_sinc(self) -> Self {
120 if self.is_zero() {
121 Self::one()
122 } else {
123 self.clone().simd_sin() / self
124 }
125 }
126
127 #[inline]
128 fn simd_sinhc(self) -> Self {
129 if self.is_zero() {
130 Self::one()
131 } else {
132 self.clone().simd_sinh() / self
133 }
134 }
135
136 #[inline]
138 fn simd_cosc(self) -> Self {
139 if self.is_zero() {
140 Self::one()
141 } else {
142 self.clone().simd_cos() / self
143 }
144 }
145
146 #[inline]
147 fn simd_coshc(self) -> Self {
148 if self.is_zero() {
149 Self::one()
150 } else {
151 self.clone().simd_cosh() / self
152 }
153 }
154
155 fn simd_log(self, base: Self::SimdRealField) -> Self;
156 fn simd_log2(self) -> Self;
157 fn simd_log10(self) -> Self;
158 fn simd_ln(self) -> Self;
159 fn simd_ln_1p(self) -> Self;
160 fn simd_sqrt(self) -> Self;
161 fn simd_exp(self) -> Self;
162 fn simd_exp2(self) -> Self;
163 fn simd_exp_m1(self) -> Self;
164 fn simd_powi(self, n: i32) -> Self;
165 fn simd_powf(self, n: Self::SimdRealField) -> Self;
166 fn simd_powc(self, n: Self) -> Self;
167 fn simd_cbrt(self) -> Self;
168
169 fn simd_horizontal_sum(self) -> Self::Element;
171
172 fn simd_horizontal_product(self) -> Self::Element;
174}
175
176impl<T: ComplexField> SimdComplexField for T {
178 type SimdRealField = T::RealField;
179
180 #[inline(always)]
181 fn from_simd_real(re: Self::SimdRealField) -> Self {
182 Self::from_real(re)
183 }
184 #[inline(always)]
185 fn simd_real(self) -> Self::SimdRealField {
186 self.real()
187 }
188 #[inline(always)]
189 fn simd_imaginary(self) -> Self::SimdRealField {
190 self.imaginary()
191 }
192 #[inline(always)]
193 fn simd_modulus(self) -> Self::SimdRealField {
194 self.modulus()
195 }
196 #[inline(always)]
197 fn simd_modulus_squared(self) -> Self::SimdRealField {
198 self.modulus_squared()
199 }
200 #[inline(always)]
201 fn simd_argument(self) -> Self::SimdRealField {
202 self.argument()
203 }
204 #[inline(always)]
205 fn simd_norm1(self) -> Self::SimdRealField {
206 self.norm1()
207 }
208 #[inline(always)]
209 fn simd_scale(self, factor: Self::SimdRealField) -> Self {
210 self.scale(factor)
211 }
212 #[inline(always)]
213 fn simd_unscale(self, factor: Self::SimdRealField) -> Self {
214 self.unscale(factor)
215 }
216 #[inline(always)]
217 fn simd_to_polar(self) -> (Self::SimdRealField, Self::SimdRealField) {
218 self.to_polar()
219 }
220 #[inline(always)]
221 fn simd_to_exp(self) -> (Self::SimdRealField, Self) {
222 self.to_exp()
223 }
224 #[inline(always)]
225 fn simd_signum(self) -> Self {
226 self.signum()
227 }
228
229 #[inline(always)]
230 fn simd_floor(self) -> Self {
231 self.floor()
232 }
233 #[inline(always)]
234 fn simd_ceil(self) -> Self {
235 self.ceil()
236 }
237 #[inline(always)]
238 fn simd_round(self) -> Self {
239 self.round()
240 }
241 #[inline(always)]
242 fn simd_trunc(self) -> Self {
243 self.trunc()
244 }
245 #[inline(always)]
246 fn simd_fract(self) -> Self {
247 self.fract()
248 }
249 #[inline(always)]
250 fn simd_mul_add(self, a: Self, b: Self) -> Self {
251 self.mul_add(a, b)
252 }
253
254 #[inline(always)]
255 fn simd_abs(self) -> Self::SimdRealField {
256 self.abs()
257 }
258 #[inline(always)]
259 fn simd_hypot(self, other: Self) -> Self::SimdRealField {
260 self.hypot(other)
261 }
262
263 #[inline(always)]
264 fn simd_recip(self) -> Self {
265 self.recip()
266 }
267 #[inline(always)]
268 fn simd_conjugate(self) -> Self {
269 self.conjugate()
270 }
271 #[inline(always)]
272 fn simd_sin(self) -> Self {
273 self.sin()
274 }
275 #[inline(always)]
276 fn simd_cos(self) -> Self {
277 self.cos()
278 }
279 #[inline(always)]
280 fn simd_sin_cos(self) -> (Self, Self) {
281 self.sin_cos()
282 }
283 #[inline(always)]
284 fn simd_sinh_cosh(self) -> (Self, Self) {
285 self.sinh_cosh()
286 }
287 #[inline(always)]
288 fn simd_tan(self) -> Self {
289 self.tan()
290 }
291 #[inline(always)]
292 fn simd_asin(self) -> Self {
293 self.asin()
294 }
295 #[inline(always)]
296 fn simd_acos(self) -> Self {
297 self.acos()
298 }
299 #[inline(always)]
300 fn simd_atan(self) -> Self {
301 self.atan()
302 }
303 #[inline(always)]
304 fn simd_sinh(self) -> Self {
305 self.sinh()
306 }
307 #[inline(always)]
308 fn simd_cosh(self) -> Self {
309 self.cosh()
310 }
311 #[inline(always)]
312 fn simd_tanh(self) -> Self {
313 self.tanh()
314 }
315 #[inline(always)]
316 fn simd_asinh(self) -> Self {
317 self.asinh()
318 }
319 #[inline(always)]
320 fn simd_acosh(self) -> Self {
321 self.acosh()
322 }
323 #[inline(always)]
324 fn simd_atanh(self) -> Self {
325 self.atanh()
326 }
327
328 #[inline(always)]
329 fn simd_sinc(self) -> Self {
330 self.sinc()
331 }
332 #[inline(always)]
333 fn simd_sinhc(self) -> Self {
334 self.sinhc()
335 }
336
337 #[inline(always)]
338 fn simd_cosc(self) -> Self {
339 self.cosc()
340 }
341 #[inline(always)]
342 fn simd_coshc(self) -> Self {
343 self.coshc()
344 }
345
346 #[inline(always)]
347 fn simd_log(self, base: Self::SimdRealField) -> Self {
348 self.log(base)
349 }
350 #[inline(always)]
351 fn simd_log2(self) -> Self {
352 self.log2()
353 }
354 #[inline(always)]
355 fn simd_log10(self) -> Self {
356 self.log10()
357 }
358 #[inline(always)]
359 fn simd_ln(self) -> Self {
360 self.ln()
361 }
362 #[inline(always)]
363 fn simd_ln_1p(self) -> Self {
364 self.ln_1p()
365 }
366 #[inline(always)]
367 fn simd_sqrt(self) -> Self {
368 self.sqrt()
369 }
370 #[inline(always)]
371 fn simd_exp(self) -> Self {
372 self.exp()
373 }
374 #[inline(always)]
375 fn simd_exp2(self) -> Self {
376 self.exp2()
377 }
378 #[inline(always)]
379 fn simd_exp_m1(self) -> Self {
380 self.exp_m1()
381 }
382 #[inline(always)]
383 fn simd_powi(self, n: i32) -> Self {
384 self.powi(n)
385 }
386 #[inline(always)]
387 fn simd_powf(self, n: Self::SimdRealField) -> Self {
388 self.powf(n)
389 }
390 #[inline(always)]
391 fn simd_powc(self, n: Self) -> Self {
392 self.powc(n)
393 }
394 #[inline(always)]
395 fn simd_cbrt(self) -> Self {
396 self.cbrt()
397 }
398
399 #[inline(always)]
400 fn simd_horizontal_sum(self) -> Self::Element {
401 self
402 }
403 #[inline(always)]
404 fn simd_horizontal_product(self) -> Self::Element {
405 self
406 }
407}